-
Notifications
You must be signed in to change notification settings - Fork 11k
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
[9.x] Add Route::singleton()
method
#44872
Conversation
* @param array $options | ||
* @return void | ||
*/ | ||
public function __construct(ResourceRegistrar $registrar, $name, $controller, array $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.
Why not use PHP 8 constructor property here
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.
This class matches the PendingResourceRegistration
class that was created prior to PHP 8.
This looks super useful, @jessarcher! |
In your examples you have routes to destroy a singleton. Shouldn't you also be able to create and store one if it doesn't exist? |
The intention would be that you'd always make a |
That makes sense, @jessarcher. |
What about Anyway, nice addition! |
Nice. I've definitely created these types of resources by hand before. My only change would be the name. If this is always a resource, which it seems to be, I'd suggest |
I think |
IMHO for some reason I think it'd be more clear if it would be named as Thank you for your work! |
I don't mind adding "resource" to the method name to give more context. I like the definition of "singleton" but I'm not married to it either. An alternative could be something like this: Route::resource('foo', FooController::class)->singleton(); // or sole, single, etc... I haven't put much thought into it, but I think the underlying code might be a little more complex if we share the same pending object for both. There are also methods on the pending resource object that would be ineffective for a singleton, like the scoping stuff. |
For some reason your last proposal while it does look better, i think it would be confusing when you'd read the routes. Having a different name at the beginning is the best route (ha!) to take. I think it provides you with a quick and direct overview instead of looking at the end to see the difference. I guess it's just a matter of naming, but I really think that |
I don't like the name |
This is a good addition. singleton is not a good name:
Better options would be |
Or even |
I like both "singleton" and "singular" as it is already an establish term for this in other frameworks. Introducing another name for it seems like fragmenting again. I feel this naming is already descriptive of the feature. "Singleton" also pops up in some JSON:API implementations (although, I don't believe this concept exists in JSON:API itself). What's more, if I see the term / function "singleResources" I'm still going to go read the docs to find out what it is, because the term itself does not tell me what it is exactly or how to use it, and if I'm source diving, the underlying code will be the same. |
It makes sense 💯 |
My vote goes to Same as in Ruby: https://guides.rubyonrails.org/routing.html#singular-resources |
The problem I have with "singular" is that we've already used that word in framework/src/Illuminate/Routing/ResourceRegistrar.php Lines 481 to 484 in 527b288
framework/src/Illuminate/Routing/ResourceRegistrar.php Lines 397 to 408 in 527b288
If we introduce a method on this class called I think I can summarize the two main problems people are having with the "singleton" name suggestion:
|
Why try to be the least verbose possible? Singular is already used. |
@jessarcher I don't think we should avoid adopting a good name because there's another similar concept in the routing component right now. I don't think these two clash enough to get confusing for users. |
Added ability to do |
I worry the word "creatable" implies that POST requests are the preferred (and perhaps only) way that a singleton resource should be created. Personally, I disagree with the other frameworks promoting the POST method on a specific resource's URI. It's like making a POST request to an individual resource in a collection (e.g. I think the HTTP spec is clear that PUT requests are specifically intended for scenarios like this. I do wish the framework world didn't have such a strong association between "PUT" and "update". The create/edit routes are less clear-cut. With a resource collection, I typically put the create form somewhere on the index route (often in a modal) rather than on a dedicated create route. So I think with a "zero or one" or "nullable" singleton, I would probably display the create form on the show route when the record doesn't exist. That would save me from having to redirect from Having said all that, I'm not completely opposed to it being opt-in. I just wonder whether there is an alternative name that doesn't imply that PUT is only for updating. Also, the irony of me objecting to naming on this PR is not lost on me 😅 |
How about Sounds idempotent to me, for example: "Set profile picture" |
I wonder when this feature will be released ? Now I am using laravel 9.33 there is no |
This PR introduces a helper to register routes for "singleton resources" - resources that are either "one of one" or "zero or one".
Example:
/profile
/profile/edit
/profile
/profile
Many of the options that apply to resource controllers can also be used here, such as
only
andexcept
:When the resource can be zero or one, a PUT request can be used for both creating and updating the resource because we always know the resource's location. The
update
name that is traditionally attached to thePUT
doesn't make this entirely clear, so we could potentially name it something likeupsert
instead. Personally, I prefer keeping the existing name rather than introducing a new action name.Singleton resources can also be nested within a standard resource for cases where a resource is singular in the scope of the parent resource:
/videos/{video}/thumbnail
/videos/{video}/thumbnail/edit
/videos/{video}/thumbnail
/videos/{video}/thumbnail
Route model binding would work for the
Video
model in the above example, but there is no model binding for singleton resources because the URL does not provide enough information to resolve it. In many cases, there may not even be a dedicated model for the singleton resource. In the above example, the thumbnail could be a separate model, but it could equally just be an attribute on theVideo
model that warrants its own routes.For parity with the
resource
methods, there is also anapiSingleton
method that excludes theedit
action, and there aresingletons
andapiSingletons
methods for bulk registration.