-
Notifications
You must be signed in to change notification settings - Fork 1.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[RFC] JSON API Errors (Initial implementation and roadmap for full feature-set) #1004
Conversation
Rubinius!!!! 😡 https://travis-ci.org/rails-api/active_model_serializers/jobs/70853922
|
I have a question about the note you made regarding " The members data and errors MUST NOT coexist in the same document.". I don't see that in the spec. What's driving that? |
|
@bf4, I see it now here: http://jsonapi.org/format/#document-top-level |
@joaomdmoura @kurko Have you had a chance to look at this? |
Hey @bf4, have just check this one. |
@joaomdmoura Thoughts about the adapters and serializers approach? And the bullet points at the top of the pr description?
|
|
||
def detail | ||
detail = object.last | ||
if detail.respond_to?(:join) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Forgive me if this is obvious, but I don't see this path of execution under test and I'm not sure why it's required. Could you share your thinking?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Basically, I'm just coding to think through what the implementation should look like, so there's cases like here where I'm not sure how I should be generating an error and details. If 'detail' should always be a string, then I need to join a collection of details, but I can't easily convert to an array due to how ActiveModel::Error behaves etc. to the join
just points out that I'm not sure what I'm dealing with :)
This PR is partly about generating discussion about how the implementation should look (in addition to actually writing it ;).
So, that's why it's not tested :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh, and @bbuchalter thanks for taking a look at this and I look forward to hearing your thoughts!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ember, a driver of the JSON api spec, notes that whereas before we might have
errors: {
first_name: ['is invalid']
}
now we'd have
errors: {
source: { pointer: 'data/attributes/first_name' },
detail: 'is invalid'
}
And you see that the field 'first_name' can have multiple errors on it
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
See https://github.com/rails-api/active_model_serializers/pull/1004/files#r36335739 where I think I figured out what it is supposed to be
Hey everyone, so I just read through the thread. |
@joaomdmoura Still working on that PR json-api/json-api#828 and then will come back here |
The json-api PR is almost done. Will continue with this then. |
The JSON API errors example is merged json-api/json-api#828 (comment) and it's live! http://jsonapi.org/examples/ |
Updated with some lessons learned with an MVP of just attribute errors, though I might want to check if they're attributes or relationships.. I just haven't thought about it yet |
@@ -0,0 +1,2 @@ | |||
class ErrorSerializer < ActiveModel::Serializer | |||
end |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure at this time if I want to assign any attributes, or just use it as a 'pass through' for the adapter to make use of the 'object' (see def object_errors
in the adapter).
7db1c3a
to
85f5c7c
Compare
class ActiveModel::Serializer::Adapter::JsonApi::Error < ActiveModel::Serializer::Adapter | ||
def serializable_hash(options = nil) | ||
options ||= {} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ref #1049
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why two blank lines?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Mistake :)
Appveyor, why? :-( |
@bf4 looks like this needs squash rebase - I can handle that if you want / need |
- ActiveModelSerializers::JsonPointer - ActiveModel::Serializer::Adapter::JsonApi::Error - ActiveModel::Serializer::Adapter::JsonApi::Error.attributes - Fix rubocop config
- Separate collection errors from resource errors in adapter - Refactor to ErrorsSerializer; first-class json error methods - DOCS - Rails 4.0 requires assert exact exception class, boo
Idea per remear (Ben Mills) in the slack: https://amserializers.slack.com/archives/general/p1455140474000171 remear: just so i understand, the adapter in `render json: resource, status: 422, adapter: 'json_api/error', serializer: ActiveModel::Serializer::ErrorSerializer` is a different one than, say what i’ve specified in a base serializer with `ActiveModel::Serializer.config.adapter = :json_api`. correct? and a followup question of, why not same adapter but different serializer? me: With the way the code is written now, it might be possible to not require a special jsonapi adapter. However, the behavior is pretty different from the jsonapi adapter. this first draft of the PR had it automatically set the adapter if there were errors. since that requires more discussion, I took a step back and made it explicit for this PR If I were to re-use the json api adapter and remove the error one, it think the serializable hash method would look like ``` def serializable_hash(options = nil) return { errors: JsonApi::Error.collection_errors } if serializer.is_a?(ErrorsSerializer) return { errors: JsonApi::Error.resource_errors(serializer) } if serializer.is_a?(ErrorSerializer) options ||= {} ``` I suppose it could be something more duckish like ``` def serializable_hash(options = nil) if serializer.errors? # object.errors.any? || object.any? {|o| o.errors.any? } JsonApi::Error.new(serializer).serializable_hash else # etc ```
@NullVoxPopuli rebased from ba8ee45 |
Hey, the checks passed! do we want to merge a partial feature, or wait? there are a few parts of the json api errors spec that I don't know how active record errors would translate (@bf4, you have notes on those in your PR Summary. At the very least, I think it would be nice to clean up all the discussion on this. |
You mean what I wrote in the pr issue? The checkboxes describe what's not done and what can be done. (No one said we need to implement everything, or that it's even a good idea to.) |
This PR is done. It will be the basis of any future error feature prs. |
Updated docs and changelog |
Ready to merge if tests pass and docs look good |
@@ -116,6 +118,10 @@ def initialize(object, options = {}) | |||
end | |||
end | |||
|
|||
def success? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what's the purpose of this?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sentinel for rendering success vs failurr doc. Search diff for usage
I think the docs look good. |
Just needs squashing |
@NullVoxPopuli I wasn't planning on squashing conmits more than currently as I wanted to tell the story of how we got here. How would you squash them? |
@bf4, fine by me. As long as the reason makes sense, I'm good with it. |
JSON API Errors (Initial implementation and roadmap for full feature-set)
❤️ |
@bf4 information here on the string format thing: jruby/jruby#3712 I guess it's just a runtime flag that was causing the issue. why do we have debug turned on in the jruby environments? it's not a huge deal regardless, I don't think, but I think it's good to log this issue for historical reasons. |
@NullVoxPopuli Thanks for the link. Those options are to make code coverage work. see https://github.com/colszowka/simplecov/blob/058dbba074d665c5ab1354582d5946fafd1c00e6/lib/simplecov.rb#L6-L15 |
gotchya -- also good to know. :-) |
Usage
Requires explicit passing of Error serializer
PR TODOS:
jsonapi/errors.md
Error object:
Serializing errors is different from resources.
ActiveModel::Error
, which we'd want to callmodel.errors.messages
on.ActiveModel::Error
is necessarily a collection of error objects, each with it's own'source'
and'detail'
Full Error API Implementation:
Implementation tests:
test/action_controller/json_api/errors_test.rb
test/action_controller/rescue_from_test.rb
rescue_with_handler
,handle_exceptions
Other implementations
ref: