I use symfony 3 and I try to manage an admin side to manage my products and my commands for my ecommerce website, but I always have the same error :
ReflectionException - Class Admin\AdminBundle\Admin\Entity\Product does not exist
this is my services :
services:
app.admin.produit:
class: Admin\AdminBundle\Admin\ProduitAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: "Content", label: "Produit" }
arguments:
- ~
- Admin\AdminBundle\Admin\Entity\Produit
- ~
calls:
- [ setTranslationDomain, [AdminAdminBundle]]
public: true
app.admin.commande:
class: Admin\AdminBundle\Admin\CommandeAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: "Content", label: "Commande" }
arguments:
- ~
- Admin\AdminBundle\Admin\Entity\Commande
- ~
calls:
- [ setTranslationDomain, [AdminAdminBundle]]
public: true
This is my CommandAdmin :
<?php
namespace Admin\AdminBundle\Admin;
use Sonata\AdminBundle\Admin\AbstractAdmin;
use Sonata\AdminBundle\Show\ShowMapper;
use Sonata\AdminBundle\Form\FormMapper;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
class CommandeAdmin extends AbstractAdmin
{
// Fields to be shown on create/edit forms
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('idProduit', 'entity', array('class' => 'Admin\AdminBundle\Entity\Produit'))
->add('date')
;
}
// Fields to be shown on filter forms
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
$datagridMapper
// ->add('idProduit')
->add('date')
;
}
// Fields to be shown on lists
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('idProduit', 'entity', array('class' => 'Admin\AdminBundle\Entity\Produit'))
->add('date')
;
}
// Fields to be shown on show action
protected function configureShowFields(ShowMapper $showMapper)
{
$showMapper
->add('idProduit')
->add('date')
;
}
}
This is my ProduitAdmin :
<?php
namespace Admin\AdminBundle\Admin;
use Sonata\AdminBundle\Admin\AbstractAdmin;
use Sonata\AdminBundle\Show\ShowMapper;
use Sonata\AdminBundle\Form\FormMapper;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
class ProduitAdmin extends AbstractAdmin
{
// Fields to be shown on create/edit forms
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('nom')
->add('description')
->add('quantite')
->add('prix')
->add('marque')
->add('fournisseur')
;
}
// Fields to be shown on filter forms
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
$datagridMapper
->add('nom')
->add('description')
->add('quantite')
->add('prix')
->add('marque')
->add('fournisseur')
;
}
// Fields to be shown on lists
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('nom')
->add('description')
->add('quantite')
->add('prix')
->add('marque')
->add('fournisseur')
;
}
// Fields to be shown on show action
protected function configureShowFields(ShowMapper $showMapper)
{
$showMapper
->add('nom')
->add('description')
->add('quantite')
->add('prix')
->add('marque')
->add('fournisseur')
;
}
}
This is the Stack Trace :
ReflectionException:
Class Admin\AdminBundle\Admin\Entity\Produit does not exist
at vendor/sonata-project/admin-bundle/Controller/CRUDController.php:480
at ReflectionClass->__construct('Admin\\AdminBundle\\Admin\\Entity\\Produit')
(vendor/sonata-project/admin-bundle/Controller/CRUDController.php:480)
at Sonata\AdminBundle\Controller\CRUDController->createAction()
at call_user_func_array(array(object(CRUDController), 'createAction'), array())
(vendor/symfony/symfony/src/Symfony/Component/HttpKernel/HttpKernel.php:153)
at Symfony\Component\HttpKernel\HttpKernel->handleRaw(object(Request), 1)
(vendor/symfony/symfony/src/Symfony/Component/HttpKernel/HttpKernel.php:68)
at Symfony\Component\HttpKernel\HttpKernel->handle(object(Request), 1, true)
(vendor/symfony/symfony/src/Symfony/Component/HttpKernel/Kernel.php:169)
at Symfony\Component\HttpKernel\Kernel->handle(object(Request))
(web/app_dev.php:29)
If someone have an idea
The error is pretty explainable: The class Admin\AdminBundle\Admin\Entity\Produit doesn't seem to exists. Take a look at your code, I guess it's not there.
My best guess would be that you mean Admin\AdminBundle\Entity\Produit (note the removed Admin\ subnamespace). The same applies to your Commande class specification just below it.
Related
I'm using Symfony and the Sonata Bundle to generate my admin interface. I have 3 classes:
Restaurant
Service
RestaurantService
With classes Restaurant and Service having a OneToMany relationship with RestaurantService.
I try RestaurantService as a child admin in Restaurant but I've got those errors:
ContextErrorException in RestaurantAdmin.php line 143:
Runtime Notice: Declaration of
GSG\AdminBundle\Admin\RestaurantAdmin::configureSideMenu() should be
compatible with
Sonata\AdminBundle\Admin\Admin::configureSideMenu(Knp\Menu\ItemInterface
$menu, $action, Sonata\AdminBundle\Admin\AdminInterface $childAdmin =
NULL)
and
FileLoaderLoadException in classes.php line 13757:
Runtime Notice: Declaration of
GSG\AdminBundle\Admin\RestaurantAdmin::configureSideMenu() should be
compatible with
Sonata\AdminBundle\Admin\Admin::configureSideMenu(Knp\Menu\ItemInterface
$menu, $action, Sonata\AdminBundle\Admin\AdminInterface $childAdmin =
NULL) in /Volumes/Data/ge0ra/www/admin_gsg/app/config/. (which is
being imported from
"/Volumes/Data/ge0ra/www/admin_gsg/app/config/routing.yml").
Here is my services.yml file:
services:
sonata.admin.restaurant:
class: GSG\AdminBundle\Admin\RestaurantAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: "Gestion des restaurants", label: "Restaurants" }
arguments:
- ~
- GSG\AdminBundle\Entity\Restaurant
- ~
calls:
- [ addChild, [#sonata.admin.restaurantservice]]
sonata.admin.service:
class: GSG\AdminBundle\Admin\ServiceAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: "Gestion des restaurants", label: "Services" }
arguments:
- ~
- GSG\AdminBundle\Entity\Service
- ~
sonata.admin.restaurantservice:
class: GSG\AdminBundle\Admin\RestaurantServiceAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: "Gestion des restaurants", label: "RestaurantServices" }
arguments:
- ~
- GSG\AdminBundle\Entity\RestaurantService
- ~
in my RestaurantAdmin class:
protected function configureSideMenu(MenuItemInterface $menu, $action, AdminInterface $childAdmin = null)
{
if (!$childAdmin && !in_array($action, array('edit'))) {
return;
}
$admin = $this->isChild() ? $this->getParent() : $this;
$id = $admin->getRequest()->get('id');
$menu->addChild(
'Voir/Editer',
array('uri' => $admin->generateUrl('edit', array('id' => $id)))
);
$menu->addChild(
'Services',
array('uri' => $admin->generateUrl('sonata.admin.restaurantservice.list', array('id' => $id)))
);
}
and my RestaurantServiceAdmin class:
class RestaurantServiceAdmin extends Admin
{
protected $parentAssociationMapping = 'Restaurant';
// Fields to be shown on create/edit forms
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('service', 'sonata_type_model')
;
}
// Fields to be shown on filter forms
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
}
// Fields to be shown on lists
protected function configureListFields(ListMapper $listMapper)
{
if (!$this->isChild())
$listMapper->addIdentifier('id')->addIdentifier('Restaurant');
$listMapper
->add('service', 'sonata_type_model')
;
}
}
Do someone have an idea from where those errors can come?
Thanks!
Your RestaurantAdmin class has the first parameter of configureSideMenu set as MenuItemInterface $menu when it should be an instance of \Knp\Menu\ItemInterface.
The Menu part of the type hint is wrong.
I got a weird result using the Sonata Admin -- list view. Here is the snapshot.
http://i.stack.imgur.com/AGmVI.png
config.yml:
# ...
sonata_admin:
title: Administration
title_logo: extras/fi.gif
sonata_block:
default_contexts: [cms]
blocks:
# Enable the SonataAdminBundle block
sonata.admin.block.admin_list:
contexts: [admin]
services.yml:
# ...
services:
sonata.department.admin:
class: %sonata.department.admin.class%
tags:
- { name: sonata.admin, manager_type: orm }
DepartmentAdmin.php
<?php
namespace Abc\Bundles\HelloBundle\Admin;
use Sonata\AdminBundle\Admin\Admin;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
use Sonata\AdminBundle\Form\FormMapper;
class DepartmentAdmin extends Admin
{
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->with('Department')
->add('name')
->end();
}
protected function configureDatagridFilter(DatagridMapper $datagridMapper)
{
$datagridMapper->add('name');
}
protected function configureListFilter(ListMapper $listMapper)
{
$listMapper->addIdentifier('name');
}
}
Entity\Department.php
//...
public function __toString()
{
$name = $this->getName();
return empty($name) ? 'Add Department' : $name;
}
The thing is, I did not integrate SonataUserBundle with this project as I find it inappropriate to the spec. Any ideas why am I getting an empty list view? For some reason, the configureListFilter is not called.
Shame on me! the issue is with the function name
configureListFilter
It should be
configureListField
waaah!.. took me long to realize that typo crap.. Thanks #AldeeMativo for the help
I'm using SonataAdmin (and Symfony2) to manage my entities. I have a oneToMany relationship between one Step and many Tasks. Since one Step can contain many Tasks, when I create a Step, I want to be able to create many Tasks and I want those tasks to be linked to this Step. To do so, I created all the proper admin classes (one for Task and one for Step).
Here's what I do that causes my problem. When I try to create a Step, I can create the tasks and even reorder them, which is great and all done automatically by SonataAdminBundle. When I click on save, everything is saved in the database, except that in the database, the id of the step is not set in the row of the Task. Therefore, the tasks are not linked to the Step...
Here's my Step's admin class:
<?php
// src/Acme/DemoBundle/Admin/PostAdmin.php
namespace IMA\ProcessManagementBundle\Admin;
use Sonata\AdminBundle\Admin\Admin;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
use Sonata\AdminBundle\Form\FormMapper;
class StepAdmin extends Admin
{
// Fields to be shown on create/edit forms
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('name', 'text', array('label' => 'Nom de l\'étape'))
->add('tasks', 'sonata_type_collection', array(), array(
'edit' => 'inline',
'inline' => 'table',
'sortable' => 'positionNumber'
))
->add('positionNumber', 'integer', array('label' => 'Position'))
;
}
// Fields to be shown on filter forms
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
$datagridMapper
->add('name')
;
}
// Fields to be shown on lists
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('name')
->add('slug')
;
}
}
Here's also my Task admin class:
<?php
// src/Acme/DemoBundle/Admin/PostAdmin.php
namespace IMA\ProcessManagementBundle\Admin;
use Sonata\AdminBundle\Admin\Admin;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
use Sonata\AdminBundle\Form\FormMapper;
class TaskAdmin extends Admin
{
// Fields to be shown on create/edit forms
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('name', 'text', array('label' => 'Tâche'))
->add('positionNumber', 'integer', array('label' => 'Position'))
;
}
// Fields to be shown on filter forms
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
$datagridMapper
->add('name')
;
}
// Fields to be shown on lists
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('name')
->add('slug')
;
}
}
Also, here are the description of my entities
IMA\ProcessManagementBundle\Entity\Step:
type: entity
table: null
fields:
id:
type: integer
id: true
generator:
strategy: AUTO
name:
type: string
length: 255
positionNumber:
type: integer
oneToMany:
tasks:
targetEntity: Task
mappedBy: step
cascade: ["persist", "merge"]
lifecycleCallbacks: { }
IMA\ProcessManagementBundle\Entity\Task:
type: entity
table: null
fields:
id:
type: integer
id: true
generator:
strategy: AUTO
name:
type: string
length: 255
positionNumber:
type: integer
manyToOne:
step:
targetEntity: Step
inversedBy: tasks
lifecycleCallbacks: { }
I'm wondering why the id of the Step is not set in the Task row...
You need to manually attach the step to the tasks, to do so you need to use the prePersist and preUpdate methods in the step admin class...
The reason for this is that the developers of the SonataAdminBundle say it's doctrine's concern to handle this and the Doctrine developers say it is the bundles responsibility... So for now we need to do it for ourselves.
This would be your new stepAdmin class:
<?php
namespace IMA\ProcessManagementBundle\Admin;
use Sonata\AdminBundle\Admin\Admin;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
use Sonata\AdminBundle\Form\FormMapper;
class StepAdmin extends Admin
{
// Fields to be shown on create/edit forms
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('name', 'text', array('label' => 'Nom de l\'étape'))
->add('tasks', 'sonata_type_collection', array(), array(
'edit' => 'inline',
'inline' => 'table',
'sortable' => 'positionNumber'
))
->add('positionNumber', 'integer', array('label' => 'Position'))
;
}
// Fields to be shown on filter forms
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
$datagridMapper
->add('name')
;
}
// Fields to be shown on lists
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('name')
->add('slug')
;
}
public function prePersist($object)
{
foreach ($object->getTasks() as $task) {
$task->setStep($object);
}
}
public function preUpdate($object)
{
foreach ($object->getTasks() as $task) {
$task->setStep($object);
}
}
}
In your Step entity you have to add in the addTask method :
class Step
{
//...
public function addTask($tasks)
{
$tasks->setStep($this);
$this->tasks[] = $tasks;
return $this;
}
//...
}
As you haven't give your Step.php you should propably adapt this code.
I have follow error when try to enter in admin dashboard:
Cannot import resource "/var/www/autoportal/app/config/." from
"/var/www/autoportal/app/config/routing.yml". (The autoloader expected
class "App\AdminBundle\Admin\AutoAdmin" to be defined in file
"/var/www/autoportal/src/App/AdminBundle/Admin/AutoAdmin.php". The
file was found but the class was not in it, the class name or
namespace probably has a typo.)
My admin class:
namespace App\AdminBundle\Admin;
use Sonata\AdminBundle\Admin\Admin;
use Sonata\AdminBundle\Datagrid\ListMapper;
use Sonata\AdminBundle\Datagrid\DatagridMapper;
use Sonata\AdminBundle\Form\FormMapper;
class AutoAdmin extends Admin
{
protected function configureFormFields(FormMapper $formMapper)
{
$formMapper
->add('name')
->add('enabled', null, array('required' => false))
;
}
protected function configureDatagridFilters(DatagridMapper $datagridMapper)
{
$datagridMapper
->add('name')
->add('posts')
;
}
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('name')
->add('slug')
->add('enabled')
;
}
}
Service configure:
services:
app_admin.auto:
class: App\AdminBundle\Admin\AutoAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: posts, label: "Auto" }
arguments:
- ~
- 'App\AutoPortalBundle\Entity\Auto'
- 'SonataAdminBundle:CRUD'
calls:
- [ setTranslationDomain, [AppAdminBundle]]
routing file:
app_auto_portal_controller:
resource: "#AppAutoPortalBundle/Controller"
type: annotation
app_auto_portal:
resource: "#AppAutoPortalBundle/Resources/config/routing.yml"
prefix: /
login:
pattern: /login
defaults: { _controller: AppAutoPortalBundle:Security:login }
login_check:
pattern: /login_check
admin:
resource: '#SonataAdminBundle/Resources/config/routing/sonata_admin.xml'
prefix: /admin
_sonata_admin:
resource: .
type: sonata_admin
prefix: /admin
On this page I found how to add route for my custom action.
protected function configureRoutes(RouteCollection $collection) {
$collection->add('ispremium', $this->getRouterIdParameter().'/ispremium');
}
After that I add custom action in my Admin class:
protected function configureListFields(ListMapper $listMapper)
{
$listMapper
->addIdentifier('id')
->add('code', null, array('label' => 'Code'))
->add('_action', 'actions', array(
'actions' => array(
'ispremium' => array(
'template' => 'AppMyBundleBundle:Admin:ispremium.html.twig'
)
)
))
;
}
It generated url like this:
/app_dev.php/admin/mobispot/discodes/discode/300876/ispremium
My template for this link:
Link
I dont' know how to solve this problems:
How to define custom controller for that route pass?
Now I have an error:
Method "Sonata\AdminBundle\Controller\CRUDController::ispremiumAction" does not exist.
Can I change generated url with generateUrl method?
When you are creating service for EntityAdmin class the third argument is the controller name. You can create a class that extends CRUDController and set it in service. e.g
The controller,
//Vendor\YourBundle\Controller\EntityAdminController.php
class EntityAdminController extends CRUDController
{
public function ispremiumAction()
{
//process
}
}
In services.yml,
entity.admin.service:
class: FQCN\Of\EntityAdmin
tags:
- { name: sonata.admin, manager_type: orm, group: your_group, label: Label }
arguments: [null, FQCN\Of\Entity, VendorYourBundle:EntityAdmin]