Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Sonata Editable List Bundle Laravel Package

aschaeffer/sonata-editable-list-bundle

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Install the Bundle

    composer require aschaeffer/sonata-editable-list-bundle
    

    Enable the bundle in config/bundles.php (Symfony Flex) or AppKernel.php (legacy):

    Aschaeffer\SonataEditableListBundle\AschaefferSonataEditableListBundle::class => ['all' => true],
    
  2. Configure Entity Classes Update config/packages/aschaeffer_sonata_editable_list.yaml:

    aschaeffer_sonata_editable_list:
        class:
            list: App\Entity\SonataEditableList
            item: App\Entity\SonataEditableItem
    
  3. Create Base Entities Use the provided SonataEditableList and SonataEditableItem entities (from the recipe branch) or create your own extending them.

  4. Initialize Lists Run the command to create a list (e.g., user_gender):

    php bin/console sonata:editable_list:create user_gender
    

    Define items via Sonata Admin or manually in the database.


First Use Case: Adding a Listable Field to an Entity

  1. Annotate the Entity Add @Listable to a property (e.g., User entity):

    use Aschaeffer\SonataEditableListBundle\Model\Listable;
    
    class User {
        /**
         * @Listable(code="user_gender")
         * @ORM\ManyToOne(targetEntity="SonataEditableItem")
         */
        protected $gender;
    }
    
  2. Configure Sonata Admin Extend configureFormFieldsProperties and configureDatagridFilters in your UserAdmin:

    use Aschaeffer\SonataEditableListBundle\Form\Type\ItemSelectorType;
    
    protected function configureFormFieldsProperties(FormMapper $formMapper) {
        $formMapper->add('gender', ItemSelectorType::class, [
            'model_manager' => $this->getModelManager(),
            'class' => SonataEditableItem::class,
            'expanded' => true,
        ]);
    }
    
  3. Test in Admin Panel Navigate to the Sonata Admin for User. The gender field should now appear as a selectable item from the predefined list.


Implementation Patterns

Workflow: Managing Editable Lists

  1. Define Lists Use the CLI or Sonata Admin to create lists (e.g., user_gender, user_interests). Example CLI command:

    php bin/console sonata:editable_list:create user_gender --items="Male,Female,Other"
    
  2. Integrate with Entities

    • One-to-Many: Use @Listable with @ORM\ManyToOne (e.g., gender).
    • Many-to-Many: Use @Listable with @ORM\ManyToMany (e.g., interests).
    • Custom Logic: Override getListableCode() in entities for dynamic list codes.
  3. Admin Integration

    • Form Fields: Use ItemSelectorType for dropdowns/checkboxes.
      $formMapper->add('interests', ItemSelectorType::class, [
          'multiple' => true, // For many-to-many
          'expanded' => true, // Checkboxes instead of dropdown
      ]);
      
    • Filters: Add listable fields to DatagridMapper for filtering:
      $datagridMapper->add('gender', null, [], ItemSelectorType::class, [
          'field_name' => 'gender',
          'class_name' => User::class,
      ]);
      
  4. Dynamic Lists Fetch lists dynamically in templates or services:

    {% set genderList = app.service('aschaeffer_sonata_editable_list.list.manager').findByCode('user_gender') %}
    

Integration Tips

  1. Sonata Admin CRUD Extend SonataEditableListAdmin and SonataEditableItemAdmin for custom list/item management.

  2. Validation Validate listable fields in entity constraints:

    use Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity;
    
    /**
     * @UniqueEntity(fields={"gender"}, message="Gender already selected")
     */
    class User {}
    
  3. Translations Store item labels in translation files (e.g., messages.en.yaml):

    user_gender:
        Male: "Mr."
        Female: "Ms."
        Other: "Other"
    

    Fetch translations in ItemSelectorType via translator.

  4. APIs Serialize listable fields in APIs using serializers:

    use JMS\Serializer\Annotation\SerializedName;
    
    class User {
        /**
         * @SerializedName("gender_label")
         */
        public function getGenderLabel() {
            return $this->gender->getLabel();
        }
    }
    

Gotchas and Tips

Pitfalls

  1. Circular Dependencies

    • Issue: Forgetting to cascade persist in @ORM\ManyToOne for SonataEditableItem can cause "detached entity" errors.
    • Fix: Always add cascade={"persist"} to listable fields:
      @ORM\ManyToOne(targetEntity="SonataEditableItem", cascade={"persist"})
      
  2. List Code Mismatches

    • Issue: Typos in @Listable(code="...") or CLI commands break list associations.
    • Fix: Validate list codes in SonataEditableListManager or use a constant:
      class User {
          const LIST_GENDER = 'user_gender';
          /**
           * @Listable(code=self::LIST_GENDER)
           */
          protected $gender;
      }
      
  3. Form Type Misconfiguration

    • Issue: ItemSelectorType fails if model_manager or class is misconfigured.
    • Fix: Pass the correct Doctrine\ORM\EntityManagerInterface:
      $formMapper->add('gender', ItemSelectorType::class, [
          'model_manager' => $this->getModelManager(), // Critical!
          'class' => SonataEditableItem::class,
      ]);
      
  4. Permission Issues

    • Issue: Users can’t edit lists/items due to missing ACLs.
    • Fix: Configure Sonata Admin security in security.yaml:
      access_control:
          - { path: ^/admin/editable_list, roles: ROLE_ADMIN }
      

Debugging

  1. Check List Existence Verify lists exist in the database:

    php bin/console doctrine:query:sql "SELECT * FROM sonata_editable_list"
    
  2. Log Form Errors Enable Symfony debug mode and check var/log/dev.log for ItemSelectorType errors.

  3. Validate Entity Mapping Use Doctrine’s schema validation:

    php bin/console doctrine:schema:validate
    

Extension Points

  1. Custom Item Selector Extend ItemSelectorType for custom UI (e.g., autocomplete):

    class CustomItemSelectorType extends ItemSelectorType {
        public function getParent() {
            return AutocompleteType::class; // Symfony UX Autocomplete
        }
    }
    
  2. Event Listeners Hook into list/item lifecycle:

    // src/EventListener/EditableListListener.php
    class EditableListListener {
        public function onPrePersist(SonataEditableItem $item) {
            $item->setCreatedAt(new \DateTime());
        }
    }
    

    Register in services.yaml:

    services:
        App\EventListener\EditableListListener:
            tags:
                - { name: doctrine.event_listener, event: prePersist }
    
  3. Custom List Providers Override SonataEditableListManager to fetch lists from external sources (e.g., API):

    class ApiEditableListManager extends SonataEditableListManager {
        public function findByCode($code) {
            $data = $this->fetchFromApi($code);
            return $this->createListFromData($data);
        }
    }
    

Configuration Quirks

  1. Caching

    • Issue: Lists aren’t updated after changes.
    • Fix: Clear the cache after modifying lists:
      php bin/console cache:clear
      
  2. Translation Fallback

    • Issue: Missing translations break item labels.
    • Fix: Set a fallback locale in config/packages/framework.yaml:
      framework:
          default_locale: en
          translator:
              fallbacks:
                  - en
      
  3. Database Schema

    • Issue: Schema updates fail due to existing data.
    • Fix: Use migrations for schema changes:
      php bin/console make:migration
      php bin/console doctrine
      
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
comsave/common
alecsammon/php-raml-parser
chrome-php/wrench
lendable/composer-license-checker
typhoon/reflection
mesilov/moneyphp-percentage
mike42/gfx-php
bookdown/themes
aura/view
aura/html
aura/cli
povils/phpmnd
nayjest/manipulator
omnipay/tests
psr-mock/http-message-implementation
psr-mock/http-factory-implementation
psr-mock/http-client-implementation
voku/email-check
voku/urlify
rtheunissen/guzzle-log-middleware