Define bundle classes via annotations or attributes

Created on 4 August 2022, over 2 years ago
Updated 3 February 2023, about 2 years ago

Problem/Motivation

Currently to declare a bundle class you have to implement hook_entity_bundle_info_alter() and set the class for each bundle. If you have many classes scattered across many modules you need to implement this many times. This can also lead to many use statements in your .module files to import all the classes just to reference the class name.

It would be a nicer experience to simply place an annotation or attribute on the bundle class.

Attributes:

<?php
#[Bundle(
  entityType: 'node',
  bundle: 'article',
  label: new TranslatableMarkup('Article'),
)]
class Article extends Node { }
?>

Annotations:

<?php
/**
 * @Bundle(
 *   entity_type = "node",
 *   bundle = "article",
 *   label = @Translation("Article"),
 * )
 */
class Article extends Node { }
?>

Steps to reproduce

N/A

Proposed resolution

The Bundle Class Annotations module provides a proof of concept using plugins. The 1.x branch supports annotations and the 2.x branch supports attributes via a patch from 📌 Use PHP attributes instead of doctrine annotations Fixed .

Such a simple feature could exist in core.

Remaining tasks

  • Determine if this is something we want in core
  • Determine if there is a better approach
  • Implement the core solution

User interface changes

N/A

API changes

Bundle Classes can be declared via annotations and/or attributes.

Data model changes

N/A

Release notes snippet

TBD

Feature request
Status

Active

Version

10.1

Component
Entity 

Last updated 1 day ago

Created by

🇦🇺Australia mstrelan

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Merge Requests

Comments & Activities

Not all content is available!

It's likely this issue predates Contrib.social: some issue and comment data are missing.

  • 🇦🇺Australia mstrelan

    #3 might not be necessary if we adopted something like https://github.com/olvlvl/composer-attribute-collector.

  • 🇮🇹Italy apaderno Brescia, 🇮🇹
  • @mstrelan opened merge request.
  • Pipeline finished with Failed
    over 1 year ago
    Total: 250s
    #41265
  • Status changed to Needs work over 1 year ago
  • 🇦🇺Australia mstrelan

    Needs work for @todo comment in system_entity_bundle_info_alter

  • Pipeline finished with Failed
    over 1 year ago
    Total: 821s
    #41266
  • Pipeline finished with Failed
    over 1 year ago
    Total: 159s
    #41268
  • Pipeline finished with Success
    over 1 year ago
    Total: 637s
    #41271
  • Status changed to Needs review over 1 year ago
  • Status changed to Needs work over 1 year ago
  • 🇺🇸United States smustgrave

    Left a comment on the MR.

    But new service seems like something that could use a CR, examples always welcome.

  • 🇩🇪Germany geek-merlin Freiburg, Germany

    Also, after having groked hook attribute discovery in a compoler pass, this should also run in a compiler pass (not as plugins).

  • 🇺🇸United States dww

    Nice! Love it. Not sure how I missed this issue, but glad to see it mentioned in Slack just now.

  • 🇦🇺Australia mstrelan

    @geek-merlin any chance you'd be able to put up an MR with that approach, even if it's only a WIP / POC?

  • 🇩🇪Germany geek-merlin Freiburg, Germany

    I doubt that i'll have time soon-ish, but how i'd approach it:
    - In ServiceProvider, register a CompilerPass
    - In CompilerPass, iterate classes in the blessed directory, check attributes, then set the collected classes as a constructor parameter of BundleClassAltererHooks service
    - In BundleClassAltererHooks, alter the bundles

  • 🇦🇺Australia larowlan 🇦🇺🏝.au GMT+10
  • 🇦🇺Australia larowlan 🇦🇺🏝.au GMT+10
  • 🇨🇭Switzerland berdir Switzerland

    With Hooks, we now have an implementation in core that doesn't use plugin discovery to find stuff, we could something like that here as well? Could then also be inlined into the EntityTypeBundleInfo, that would also make it clear that you're not meant to use this directly as an API.

    The discovery should probably make sure that it's not possible to register multiple classes for the same bundle. Can also happen with the alter hook, where it's much harder to detect, but at least here we could?

    What about subclasses? Lets say a contrib module defines a node type and adds a bundle class for it. In a custom project you want to subclass and change that. I guess you still have the option to use the alter hook then and set it there.

  • 🇦🇺Australia dpi Perth, Australia

    The discovery should probably make sure that it's not possible to register multiple classes for the same bundle. Can also happen with the alter hook, where it's much harder to detect, but at least here we could?

    What about subclasses? Lets say a contrib module defines a node type and adds a bundle class for it. In a custom project you want to subclass and change that. I guess you still have the option to use the alter hook then and set it there.

    Maybe you'd be interested in reviewing Add logic to determine which bundle class should take effect when multiple classes extend the same bundle Active and associated PR.

  • Merge request !11545Bundle attribute with compiler pass → (Open) created by mstrelan
  • Pipeline finished with Failed
    21 days ago
    Total: 112s
    #452774
  • Pipeline finished with Failed
    21 days ago
    Total: 121s
    #452776
  • Pipeline finished with Failed
    21 days ago
    Total: 158s
    #452785
  • Pipeline finished with Success
    21 days ago
    Total: 531s
    #452791
  • 🇦🇺Australia mstrelan

    Added a new branch (MR !11545) that adds a container pass for collecting bundle classes and registers them in EntityTypeBundleInfo. It's very rough, so I'm looking for advice on how to improve it, e.g. with caching and just general improvements, as well as pointing out everything I did wrong.

  • Added comments to the MR with a few thoughts.

Production build 0.71.5 2024