Skip to content

Conversation

@richmolj
Copy link
Contributor

There are a number of use cases - such as getting the current user -
where Resources and other objects need access to the context (in Rails,
the context is the controller). Resource#with_context made sure the
context was available for filter guards, for example.

This is now the same dev-facing API, but the context is set on
Thread.current rather than the Resource instance. This is because the
same context needs to be available to all nested resources, serializers,
etc. 'context' is more of a global concept, and this code treats it as
such.

The final product is you can do something like this in a Resource:

def create(attributes)
  raise 'not authorized!' unless context.current_user.role == 'admin'
  super
end

...regardless of whether this resource is being created from its
corresponding endpoint, or side-posted 3 levels deep.

There are a number of use cases - such as getting the current user -
where Resources and other objects need access to the context (in Rails,
the context is the controller). Resource#with_context made sure the
context was available for filter guards, for example.

This is now the same dev-facing API, but the context is set on
Thread.current rather than the Resource instance. This is because the
same context needs to be available to all nested resources, serializers,
etc. 'context' is more of a global concept, and this code treats it as
such.

The final product is you can do something like this in a Resource:

```ruby
def create(attributes)
  raise 'not authorized!' unless context.current_user.role == 'admin'
  super
end
```

...regardless of whether this resource is being created from its
corresponding endpoint, or side-posted 3 levels deep.
@richmolj richmolj merged commit 32efce5 into jsonapi-suite:master May 18, 2017
@ethier
Copy link

ethier commented Jun 3, 2017

This is great, thanks for the hard work on this.

Any way that context is available to jsonapi_create? Specifically, trying to chain the creation of an object in the controller e.g:

This:

def create
  email, success = jsonapi_create.to_a

  if success
    render_jsonapi(email, scope: false)
  else
    render_errors_for(email)
  end
end

For this:

def create
  email = **current_user.emails.create(strong_resource)**

  if success
    render_jsonapi(email, scope: false)
  else
    render_errors_for(email)
  end
end

Should this be done in the resource instead?

@richmolj
Copy link
Contributor Author

richmolj commented Jun 3, 2017

@ethier so you're trying to create an email for the current user? I'd do it in the resource, yes:

class EmailResource < ApplicationResource
  def create(attrs)
    attrs.merge!(user_id: context.current_user.id)
    super(attrs)
  end
end

Would that work for you?

@ethier
Copy link

ethier commented Jun 5, 2017

@richmolj That's perfect. Exactly what I was looking for. Makes sense that context is available in the controller mixin. Didn't think of it! Thanks.

@BjornMelgaard Thanks for the help. That's useful too. The particular request includes meta/relationships so you're example wouldn't quite work. Handy though!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants