onkbear / backpack-nested-crud Goto Github PK
View Code? Open in Web Editor NEWNested CRUD operations field for Laravel Backpack v4
License: MIT License
Nested CRUD operations field for Laravel Backpack v4
License: MIT License
Do you have any plans to upgrade to Laravel 7.0. It is giving error with "ajax" routes and the "nestedStore", it is saying that it is duplicated and do not let clear the cache of the routes "php artisan route: cache".
Message:
In AbstractRouteCollection.php line 210:
Unable to prepare route [my-main-form/{id}/detail-form/ajax] for serialization. Another route has a
lready been assigned name [detail-form.nestedStore].
There is a problem while using the image field in the nested crud.
The first problem is that I can't resize the image.
The second problem is that sometimes upload succeeded and sometimes failed
do you have any idea to fix this?
Thanks for your work is awesome. If I solved I will send you the PR.
Hi.
Nice work with this project.
I'm having some trouble with the the operation NestedCreateOperation
. The other operations work beautifully.
My models are defined as follows (with the conventions expected by Eloquent), where an item can have multiple references:
items
id
name
references
id
item_id
url
When I try to add a new reference from the modal, I get the following error:
SQLSTATE[HY000]: General error: 1364 Field 'item_id' doesn't have a default value (SQL: insert into
references
(url
) values (http://example.com)) {"exception":{"errorInfo":["HY000",1364,"Field 'item_id' doesn't have a default value"]}}
In fact the column item_id
is not nullable and is defined as a foreign key to items.id
.
The POST request contains this ID in the URL (http://localhost/admin/item/1/reference/ajax). Should it be sent in the body just like the url
field?
It works fine if I add the item_id
field in setupNestedCreateOperation()
and fill manually it in the form.
Since this is basic functionality and similar to the example in the README, I think I should be doing something wrong. Please check my changes below.
The changes in my custom routes:
@@ -15,7 +15,11 @@
'namespace' => 'App\Http\Controllers\Admin',
], function () { // custom admin routes
Route::crud('tag', 'TagCrudController');
Route::crud('author', 'AuthorCrudController');
Route::crud('item', 'ItemCrudController');
Route::crud('reference', 'ReferenceCrudController');
+
+ Route::group(['prefix' => 'item/{item_id}'], function() {
+ Route::crud('reference', 'ItemReferenceCrudController');
+ });
}); // this should be the absolute last line of this file
The changes in my ItemCrudController
:
@@ -135,12 +135,21 @@
* @see https://backpackforlaravel.com/docs/crud-operation-update
* @return void
*/
protected function setupUpdateOperation()
{
$this->setupCreateOperation();
+
+ CRUD::addField([
+ 'name' => 'references',
+ 'label' => 'References',
+ 'type' => 'nested_crud',
+ 'target' => 'reference',
+ 'model' => \App\Models\Reference::class,
+ ]);
+
}
protected function fetchAuthor()
{
return $this->fetch(\App\Models\Author::class);
}
And my new ItemReferenceCrudController
<?php
namespace App\Http\Controllers\Admin;
use Backpack\CRUD\app\Http\Controllers\CrudController;
use Backpack\CRUD\app\Library\CrudPanel\CrudPanelFacade as CRUD;
use App\Http\Requests\ReferenceRequest;
class ItemReferenceCrudController extends CrudController {
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedListOperation;
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedCreateOperation;
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedUpdateOperation;
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedDeleteOperation;
public function setup() {
CRUD::setModel(\App\Models\Reference::class);
// get the item_id parameter
$item_id = \Route::current()->parameter('item_id');
// set a different route for the admin panel buttons
CRUD::setRoute(config('backpack.base.route_prefix').'/item/'.$item_id.'/reference');
// show only that item's references
CRUD::addClause('where', 'item_id', $item_id);
}
protected function setupNestedListOperation()
{
CRUD::addColumns(['url']);
}
protected function setupNestedCreateOperation()
{
CRUD::setValidation(ReferenceRequest::class);
CRUD::addFields([
[
'name' => 'url',
'type' => 'url',
]
]);
}
protected function setupNestedUpdateOperation()
{
$this->setupNestedCreateOperation();
}
}
Just for hacking purposes, I've made this nasty change to vendor/onkbear/backpack-nested-crud/src/app/Http/Controllers/Operations/NestedCreateOperation.php
. It worked.
@@ -68,13 +68,18 @@
{
$this->crud->hasAccessOrFail('create');
// execute the FormRequest authorization and validation, if one is required
$request = $this->crud->validateRequest();
+ $data = $this->crud->getStrippedSaveRequest();
+
+ $data['item_id'] = \Route::current()->parameter('item_id');
+
// insert item in the db
- $item = $this->crud->create($this->crud->getStrippedSaveRequest());
+ $item = $this->crud->create($data);
+
$this->data['entry'] = $this->crud->entry = $item;
return $item->getKey();
}
}
Edit 1
It also works with this hackish override of the trait method nestedStore()
:
public function nestedStore()
{
$this->crud->setOperationSetting('saveAllInputsExcept', ['my_input_name', '_token', '_method', 'http_referrer', 'current_tab', 'save_action']);
$itemId = \Route::current()->parameter('item_id');
request()->merge(['item_id'=>$itemId]);
return $this->traitNestedStore();
}
Edit 2
It also works if I explicitly set a hidden field with the correct value. This is not mentioned in the documentation. Should it be?
protected function setupNestedCreateOperation()
{
CRUD::setValidation(ReferenceRequest::class);
$itemId = \Route::current()->parameter('item_id');
CRUD::addFields([
[
'name' => 'url',
'type' => 'url',
],
[
'name' => 'item_id',
'type' => 'hidden',
'value' => $itemId,
],
]);
}
Thank you for your time.
Prevent Add more than one record in 1-1 relations
I update to version 1.0.3 and show this message:
In AbstractRouteCollection.php line 210:
Unable to prepare route [admin/user/{user_id}/comment/ajax/{id}/translate/{lang}] for serialization. Another route has already been assigned name [comment.translateItem].
Thanks!
There is a problem while using upload field in nested crud?
the file doesn't appear in the request.
could you please help ?
Thank you for your job, it solved a lot of my difficulties on my project.
This is not an issue, maybe it's just something that i can't figure out.
I was following your example and created an 'Entity' with Model and CRUDController and the nested 'subEntity' with its Model and CRUDController (for reference, Entities are electonic devices and the nested 'sub-entities' are network cards that could be installed or not inside the device, and could be more than once).
It works flawlessy on edit/update operation: from the list of devices i edit the one that i need to modify, i change the device fields and i see the nested fields related to the Network Cards installed into that device; i can edit, delete and add new fields without problems.
The problem comes when i create a new device! i fill all the fields of the device, but the "Network Cards" tab is empty, neither the "add new" button, no CRUDs; i expect the nested "list" view of the sub-entity (network cards), obviously empty but with the possibility to add new elements.
I'm a newbie on Laravel, but I suspect there is something missing in the Routes.
Here's my custom.php:
Route::group([
'prefix' => config('backpack.base.route_prefix', 'admin'),
'middleware' => [
config('backpack.base.web_middleware', 'web'),
config('backpack.base.middleware_key', 'admin'),
],
'namespace' => 'App\Http\Controllers\Admin',
], function () { // custom admin routes
Route::crud('devicefield', 'DeviceFieldCrudController');
Route::crud('devicefieldtype', 'DeviceFieldTypeCrudController');
Route::crud('deviceform', 'DeviceFormCrudController');
Route::crud('device', 'DeviceCrudController');
Route::group([
'prefix' => 'device/{device_id}'], function() {
Route::crud('devicenetworkcard', 'DeviceNetworkcardCrudController');
});
});
DeviceCrudController.php:
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Requests\DeviceRequest;
use Backpack\CRUD\app\Http\Controllers\CrudController;
use Backpack\CRUD\app\Library\CrudPanel\CrudPanelFacade as CRUD;
use Illuminate\Support\Facades\DB;
class DeviceCrudController extends CrudController
{
use \Backpack\CRUD\app\Http\Controllers\Operations\ListOperation;
use \Backpack\CRUD\app\Http\Controllers\Operations\CreateOperation;
use \Backpack\CRUD\app\Http\Controllers\Operations\UpdateOperation;
use \Backpack\CRUD\app\Http\Controllers\Operations\DeleteOperation;
use \Backpack\CRUD\app\Http\Controllers\Operations\ShowOperation;
public function setup()
{
CRUD::setModel(\App\Models\Device::class);
CRUD::setRoute(config('backpack.base.route_prefix') . '/device');
CRUD::setEntityNameStrings('device', 'devices');
}
protected function setupListOperation()
{
//$this->crud->setFromDb();
// ...
}
protected function setupCreateOperation()
{
CRUD::setValidation(DeviceRequest::class);
CRUD::field('sd_marcacentrale');
CRUD::field('sd_modellocentrale');
// .....
CRUD::addField([
'name' => 'devicenetworkcards',
'label' => 'Schede di rete',
'type' => 'nested_crud',
'target' => 'devicenetworkcard',
'model' => 'App\Models\DeviceNetworkcard',
'tab' => 'Rete',
]);
}
protected function setupUpdateOperation()
{
$this->setupCreateOperation();
}
protected function setupShowOperation()
{
$this->crud->set('show.setFromDb', true);
}
}
DeviceNetworkcardCrudController:
<?php
namespace App\Http\Controllers\Admin;
use App\Http\Requests\DeviceNetworkcardRequest;
use Backpack\CRUD\app\Http\Controllers\CrudController;
use Backpack\CRUD\app\Library\CrudPanel\CrudPanelFacade as CRUD;
use Illuminate\Support\Facades\DB;
class DeviceNetworkcardCrudController extends CrudController
{
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedListOperation;
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedCreateOperation;
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedUpdateOperation;
use \Onkbear\NestedCrud\app\Http\Controllers\Operations\NestedDeleteOperation;
public function setup()
{
CRUD::setModel(\App\Models\DeviceNetworkcard::class);
$deviceId = \Route::current()->parameter('device_id');
CRUD::setRoute(config('backpack.base.route_prefix').'/device/'.$deviceId.'/devicenetworkcard');
CRUD::addClause('where', 'device_id', $deviceId);
CRUD::setEntityNameStrings('devicenetworkcard', 'device_networkcards');
}
protected function setupNestedListOperation()
{
$this->crud->setListView('nested_crud::nested_list');
//$this->crud->setFromDb();
CRUD::column('ip');
CRUD::column('subnet');
CRUD::column('gateway');
//CRUD::column('device_id');
//CRUD::column('created_at');
//CRUD::column('updated_at');
}
protected function setupNestedCreateOperation()
{
CRUD::setValidation(DeviceNetworkcardRequest::class);
// get the device_id parameter
$deviceId = \Route::current()->parameter('device_id');
//$this->crud->setFromDb();
//Network card fields:
CRUD::field('device_id');
CRUD::field('ip');
CRUD::field('subnet');
CRUD::field('gateway');
// add a foreign key field as a hidden field (may need only for create operation)
CRUD::addField([
'name' => 'device_id',
'type' => 'hidden',
'value' => $deviceId
]);
}
protected function setupNestedUpdateOperation()
{
//CRUD::setValidation(DeviceNetworkcardRequest::class);
$this->setupNestedCreateOperation();
}
}
Hope you understand what i need.
Please help me, I know i will have further problems with the 'list' operation but i don't want to think about it for now :)
Many thanks
Hi, are you interested in migrating to backpack version 5?
Hi,
Wonderful feature, great job !
I just test it on a polymorphic one to many, it's working great
However i need to add search and filters in the nested crud list. I tried the backpack way but it's not showing.
Am I doing something wrong or is this feature not implemented yet ?
Thanks in advance
Capture some GIF.
Hi, I am try to use select2_from_ajax, but not permit write text in the box and select listed items. See the code:
$this->crud->addField([ 'label' => "Cรณd.Norma Referida", 'type' => 'select2_from_ajax', 'name' => 'cod_norma_referida', 'entity' => 'vinculoReferente', 'attribute' => 'name', 'data_source' => url("/get-select-data"), 'placeholder' => 'Select option', 'minimum_input_length' => 0,/*I try with 1,2,3,4,5...*/ 'method' => 'GET', 'include_all_form_fields' => true, /*I try enable and disable*/ ]);
And the route:
Route::get('/get-select-data', [ NormaCrudController::class, 'getSelectData']);
And the function getSelectData:
public function getSelectData(Request $request) { $search_term = $request->input('q'); if ($search_term) { $results = Norma::select('name', 'id')->where('name', 'LIKE', '%'.$search_term.'%')->orderBy('id','asc')->paginate(10); } else { $results = Norma::select('name', 'id')->orderBy('id','asc')->paginate(10); } return $results; }
Hi there,
I am receiving the following error on the ajax route when loading the page.
"message": "call_user_func_array() expects parameter 1 to be a valid callback, first array member is not a valid class name or object"
It seems to be tied to this line 'CRUD::addClause('where', 'client_id', $client_id);'
I have slightly modified the code for my situation, 'user' was changed to 'client' and 'comment' was changed to 'order' and all of the relations have been setup.
I have tried adding `dd($client_id)' before this line and it rightfully displays the client_id in the Backpack edit screen.
This appears to be similar to Laravel-Backpack/CRUD#2049 however I cannot figure out how to change this so it works with the nested_crud
This is on
Laravel 7 Backpack 4.1 Nested_Crud 2.0
you need to add select to
container.children('input, textarea, select').addClass('is-invalid');
in nested_crud.blade.php file. line 116
When I tried to make the Request required then after tried to submit with null data and the notification will be like this:
and another bug, it not only made multiple warning on on-the-fly method but in the normal form the warning will be showing too:
that because have the same name attribute, that's why it will modify the normal form too
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.