Backpack 4.1 Routes syntax - laravel

I'm updating Laravel 5.4 to Laravel 8, so far everything goes "well" it's time consuming but the upgrade worth it.
My problem is that I don't know Backpack very well and the upgrade is considerable.
I'm now stuck with the new route syntax, there where a CRUD::resource facade that handled route customization that is not available anymore.
What would be the right approach for the following "simplified" custom route files. (I removed everything I figured already)
Route::group([
'prefix' => config('backpack.base.route_prefix', 'admin'),
'middleware' => [
'web',
config('backpack.base.middleware_key', 'admin'),
],
'namespace' => 'App\Http\Controllers\Admin',
], function() { // custom admin routes
Route::get('report', function() {
$clients = ClientWithSubscription::get();
$clientsT = transformer()->transform($clients);
return view('clients')->withClients($clientsT['data']);
});
// Client
CRUD::resource('client', 'ClientCrudController');
Route::group(['prefix' => 'client/{client_id}'], function() {
CRUD::resource('address', 'ClientAddressCrudController');
CRUD::resource('subscription', 'ClientSubscriptionCrudController');
});
// Taxonomy
foreach (['theme', 'tag', 'subject', 'utility', 'document_type', 'special_need', 'level', 'platform', 'other', 'shop',] as $taxonomy) {
CRUD::resource('taxonomy/' . $taxonomy, 'TaxonomyCrudController');
}
// Items
CRUD::resource('item/document', 'ItemDocumentCrudController');
// Referrals
CRUD::resource('referrals', 'ReferralCrudController')->with(function() {
Route::post('referrals/mark-paid/{id?}', 'ReferralCrudController#markPaid');
Route::post('referrals/mark-unpaid/{id?}', 'ReferralCrudController#markUnpaid');
Route::post('referrals/edit-notes/{id}', 'ReferralCrudController#editNotes');
});
});
My questions are
How do I add a prefix to all crud route ?
If a CrudController use default route, then it mean I don't need to declare it at all, Backpack will take care of it ?
How do I add custom method to the CRUD Route ?
Thank you!

Two changes are needed:
instead of CRUD::resource('item/document', 'ItemDocumentCrudController'); you should now do Route::crud('item/document', 'ItemDocumentCrudController');
the extra routes inside the ->with() closures should be moved after the appropriate Route::crud() statement;
See this step in the Backpack upgrade process for more details.
Also, make sure to upgrade to Backpack 4.0 (using its upgrade guide), and only after it's working to upgrade to Backpack 4.1 (the latest version).

Related

Can't seem to find a way to use the route.php from 5.2 from laravel 5.2 to 8.83.25 web.php

I'm pretty new with Laravel, was able to work on finding a tutorial but it uses a
5.2 version.
I'm trying to convert the older version to 8.83.25
This is the route in the tutorial that I'm following.
I have created the CategoryController.php manually
Route::group(['middleware' => ['web']], function(){
Route::get('category', 'CategoryController');
});
What you used is wrong syntax. To pass a route to a controller, you are supposed to pass it as an array as such:
Route::group(['middleware' => ['web']], function(){
Route::get('category', [CategoryController::class]);
});
Now supposing you want to pass it to a particular function(lets say the function store) in your controller, you just indicate that in the array as such:
Route::group(['middleware' => ['web']], function(){
Route::get('category', [CategoryController::class, 'store']);
});
Take a look at the docs to learn more about laravel v8 routing.

How to add simple view other than Crud to Laravel Backpack

I'm trying to figure out how to add a simple view (without CRUD) to Laravel Backpack. I've found this article, however I can't make it work.
I have added new controller and view, however I'm getting following error:
Method App\Http\Controllers\Admin\RaportyController::setupRoutes does not exist.
I don't understand the routes, what should I add to make it work?
Thank you
EDIT
I've changed the ::crud to ::get in my routes and I'm getting a different error: App\Http\Controllers\Admin\RaportyParkingoweController is not invokable.
My routes (custom.php) file:
<?php
// --------------------------
// Custom Backpack Routes
// --------------------------
// This route file is loaded automatically by Backpack\Base.
// Routes you generate using Backpack\Generators will be placed here.
Route::group([
'prefix' => config('backpack.base.route_prefix', 'admin'),
'middleware' => array_merge(
(array) config('backpack.base.web_middleware', 'web'),
(array) config('backpack.base.middleware_key', 'admin')
),
'namespace' => 'App\Http\Controllers\Admin',
], function () { // custom admin routes
Route::crud('opinie', 'OpinieCrudController');
Route::crud('rezerwacje', 'RezerwacjeCrudController');
Route::crud('uzytkownicy', 'UzytkownicyCrudController');
Route::get('raporty', 'RaportyController');
}); // this should be the absolute last line of this file
It should be a simple fix, point to the method you want in that controller: when you're using Route::get(), make sure to also specify the method you want to point to. It should be Route::get('RaportyParkingoweController#yourMethodName');, not Route::get('RaportyParkingoweController');.

Laravel 7 automatic scoping in resource route

is there a way to use the new automatic scoping in resource routes? Everything I tried didn't work:
Route::apiResource('instances/{instance:id}/projects', 'ProjectController', [
'except' => ['destroy']
]);
The following manual solution is working but would be a mess in the routes file.
Route::get('instances/{instance:id}/project/{project:id}',function(Instance $instance, Project $project){
return response()->json($project);
});
Thanks
I had a similar problem and as far as I can tell, the custom route key needs to be specified on the nested resource to trigger automatic scoping. The easiest way to do it without specifying each route separately is probably using parameters():
Route::apiResource('instances.projects', 'ProjectController')->parameters([
'projects' => 'project:id'
]);
it is probably help you
Route::group(['prefix' => 'instances/{instance:id}'], function () {
Route::apiResource('project', 'ProjectController', [
'except' => ['destroy']
]);
});
it could be an issue your models are in some other directory. you have to resolve the models first to be injected.
public function boot()
{
parent::boot();
Route::model('instance', App\Instance::class);
Route::model('project', App\Project::class);
}
You have to explicitly bind the models to keys.
Route::get('instances/{instance:id}/project/{project:id}',function(Instance $instance, Project $project){
return response()->json($project);
});

Laravel optional prefix routes with regexp

Is there a way to create routes with prefixes so I can have routes like this
/articles.html -> goes to listing Controller in default language
/en/articles.html -> goes to the same controller
/fr/articles.html -> goes to the same controller
My current problem is that by doing:
Route::group(['prefix=>'/{$lang?}/',function(){});
a route like this: /authors/author-100.html will match a prefix 'authors` , and for sure there is no language called "authors".
I use laravel 5.5
There doesn't seem to be any good way to have optional prefixes as the group prefix approach with an "optional" regex marker doesn't work. However it is possible to declare a Closure with all your routes and add that once with the prefix and once without:
$optionalLanguageRoutes = function() {
// add routes here
}
// Add routes with lang-prefix
Route::group(
['prefix' => '/{lang}/', 'where' => ['lang' => 'fr|en']],
$optionalLanguageRoutes
);
// Add routes without prefix
$optionalLanguageRoutes();
This should be sufficient using the where Regex match on the optional route parameter:
Route::get('/{lang?}, 'SameController#doMagic')->where('lang', 'en|fr');
You can do the same on Route Group as well, else having all the options as in this answer evidently works.
An update to show the use of prefix:
Route::group(['prefix' => '{lang?}', 'where' => ['lang' => 'en|fr']],function (){
Route::get('', 'SameController#doNinja');
});
As far as I am concerned this should be sufficient even when there is no lang as well as when there is one, just maybe this group could come before other routes.
You can use a table to define the accepted languages and then:
Route::group([
'prefix' => '/{lang?}',
'where' => ['lang' => 'exists:languages,short_name'],
], function() {
// Define Routes Here
});
Another working solution would be to create an array of langs and loop over it:
$langs = ['en', 'fr', ''];
foreach($langs as $lang) {
Route::get($lang . "/articles", "SomeController#someMethod");
}
For sure this makes your route file less readable, however you may use php artisan route:list to clearly list your routes.

Unused parameters in routes Laravel 5.1

I write api for mobile, since I have more than one version, I don't want to copy-paste the same routes, hence I decided to do something like this:
Route::model('callRequestNote', CallRequestNote::class);
Route::group([
'prefix' => 'api/v{version}/mobile',
'where' => ['version' => '[1|2]'],
], function () {
Route::delete('/notes/{callRequestNote}', MobileNotesController::class . '#destroy');
// other duplicated routes
});
public function destroy($version, CallRequestNote $callRequestNote)
{
//
}
I use version parameter only in BeforeMiddleware, hence I don't need it in controller. My question is how to replace those parameters and make CallRequestNote as a first argument and get rid of $version?

Resources