Skip to content

Singular Resources #10

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

Closed
lindyhopchris opened this issue Apr 27, 2016 · 9 comments
Closed

Singular Resources #10

lindyhopchris opened this issue Apr 27, 2016 · 9 comments
Milestone

Comments

@lindyhopchris
Copy link
Member

Add support for registering routes of singular resources:
http://discuss.jsonapi.org/t/does-jsonapi-love-singular-resources/125/5

@dtr0yan
Copy link
Contributor

dtr0yan commented Feb 20, 2017

Hi @lindyhopchris
I think it can be easily implemented by commenting
throw new RuntimeException('No matching resource type from the current route name.');
in RequestInterpreter class.

So after this we can add any route we want and place custom actions in same controller.

With this solution I added /users/me route and map it to method in UsersController class. This class extend EloquentController and serve all json-api stuff.

Is it good solutions? Or not? What side effects can we get with such solution?

Thanks in advance

@dtr0yan
Copy link
Contributor

dtr0yan commented Feb 21, 2017

or maybe @jstoone have thoughts about this

@lindyhopchris
Copy link
Member Author

If that works at the moment then I suppose it might be acceptable at the moment.

I think the more permanent solution going forward would be to use the options when registering the JSON-API resource with the route JsonApi::resource('users') to pass in something that registers me as an extra route on the same controller.

That should be fairly straight-forward to do, but we'd then need to follow through what happens with all the parsing of the request to check that it doesn't start throwing exceptions elsewhere. The main problem is that because the endpoint is not defined in the spec, it's not really possible to know how to validate the request content for a POST or PUT request.

@jstoone
Copy link
Contributor

jstoone commented Feb 21, 2017

This sounds like a really neat feature!

The first thought that hit me, was that these singular resources sound very much like an alias to me. And since the singular resources are ideally going to be quite few, I'd actually suggest an implementation that could fit in either the RouteServiceProvider or route file without being to intrusive, which would allow us to achieve a resource alias api like:

// The array key is the JSON:API `resourceType`
// The array value is the ID identifier for the resource
// The last string argument is the final alias to get the resource

JsonApi::resourceAlias(
    ['users' => auth()->id()]
    '/users/me'
);

NB: for simplicity sake lets assume the currently authenticated user has an ID of 5
Then we can logically keep it simple:

  • Register alias within a container
  • When request arrives we can check if the resource type has an alias
    • In this case the resource type is users
  • If we have an alias, we can transform the current aliased request to the specific path
    • In the example above we would transform from /users/me to /users/5
  • Now we can continue processing as if the request was /users/5 from the start

I might not have understood or not think the solution through, so I hope it makes sense @dmitry-php @lindyhopchris. 😄

@jstoone
Copy link
Contributor

jstoone commented Mar 1, 2017

@lindyhopchris I think I'll start taking a look at this, and then we can iterate if it does not seem to fit the style you have in mind. 🙂

All of a sudden laravel-json-api got a lot of activity. Nice! Let the work begin! 😅

@lindyhopchris
Copy link
Member Author

@jstoone sorry, meant to reply earlier. The alias won't work because you won't have the authenticated user id at the time that you are registering routes.

@jstoone
Copy link
Contributor

jstoone commented Mar 1, 2017

@lindyhopchris hmm maybe we could enable the resource value to be a closure? In that way we could evaluate the value when transforming the aliased request?

@lindyhopchris
Copy link
Member Author

Closures won't be compatible with route:cache.

I think it's some sort of config in the options that can be passed to JsonApi::resource() that registers these additional routes to a specific method on the controller. But not sure right at this moment what that might be.

Also I'm planning to make some changes to the routing stuff so that the current $hasMany and $hasOne properties on the Request object actually get used when registering the routes. So it might be better to wait until I've made that change before thinking about how we also do singular resources? Or change both at once?

@lindyhopchris lindyhopchris added this to the 1.0.0 milestone Mar 27, 2018
@lindyhopchris lindyhopchris modified the milestones: 1.0.0, 1.1.0 May 6, 2018
@lindyhopchris lindyhopchris modified the milestones: 1.1.0, 1.0.0 Jan 19, 2019
@lindyhopchris
Copy link
Member Author

Closing this as it is effectively solved via #196

I.e. in 1.0.0-rc.1 you'll be able to add custom actions for a resource, so you could do this to add a me route for the users resource:

JsonApi::register('default')->withNamespace('Api')->routes(function ($api) {
    $api->resource('users')->controller()->routes(function ($posts) {
        $posts->get('me', 'current');
    });
});

Which would mean GET /api/users/me would be handled by the Api\UsersController@current action.

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

No branches or pull requests

3 participants