Теперь в Cycle ORM для описания схемы наравне с аннотациями можно использовать атрибуты.
Плавность перехода с аннотаций на атрибуты обеспечат:
- В аннотациях и атрибутах используются одни и те же классы, с теми же параметрами.
- По умолчанию аннотации можно использовать совместно с атрибутами.
- Совместимость с PHP >=7.2
Несмотря на то, что атрибуты нативно поддерживаются только с PHP 8, начинать использовать их можно уже сейчас.
Одно лишь условие: каждый атрибут должен умещаться в одной строке, иначе вы получите синтаксическую ошибку на ранних версиях php.
Аннотация @Entity
/**
* @Entity(role = "eComplete", mapper = "CompleteMapper", repository = "Repository/CompleteRepository")
*/
class Complete
{
}
Аналогичный атрибут
#[Entity(role: "eComplete", mapper: CompleteMapper::class, repository: "Repository/CompleteRepository")]
class Complete
{
}
PHP 8 не позволяет вкладывать атрибуты в атрибуты, поэтому некоторые параметры, ранее подразумевающие вложенность, вынесены отдельно.
Было
/**
* @Entity()
* @Table(
* columns = {
* "name": @Column(type="string"),
* "status": @Column(type="enum(active,disabled)", default="active")
* },
* indexes = {
* @Index(columns={"status"}),
* @Index(columns={"name"}, unique=true, name="name_index")
* }
* )
*/
class Entity
{
}
Стало
#[Entity]
#[Column(name: 'name', type: 'string')]
#[Column(name: 'status', type: 'enum(active,disabled)', default: 'active')]
#[Index(columns: ['status'])]
#[Index(name: "name_index", columns: ['name'], unique: true)]
class Entity
{
}
В случае аннотаций вынос параметров тоже будет работать:
/**
* @Entity()
* @Column(name="name", type="string"),
* @Column(name="status", type="enum(active,disabled)", default="active")
* @Index(columns={"status"}),
* @Index(columns={"name"}, unique=true, name="name_index")
*/
class Entity
{
}
Параметр inverse
для связей также вынесен в отдельный атрибут.
Было
class Before
{
/**
* @HasOne(target=Simple::class, load="eager", inverse = @Inverse(as="user", type="belongsTo", load="lazy"))
*/
protected $simple;
}
Стало (Аннотации)
class After
{
/**
* @HasOne(target=Simple::class, load="eager")
* @Inverse(as="user", type="belongsTo", load="lazy")
*/
protected $simple;
}
Стало (Атрибуты)
class After
{
#[HasOne(target: Simple::class, load: "eager")]
#[Inverse(as: "user", type: "belongsTo", load: "lazy")]
protected $simple;
}
Вы можете использовать совместно и атрибуты, и аннотации, пока не завершите миграцию:
#[Entity(role: 'user_post')]
class Post
{
#[Column(type: 'primary')]
protected $id;
/** @ManyToMany(target="Tag", though="Tag/Context", orderBy={"id": "DESC"}) */
protected $tags;
/** @Embedded(target="Metadata", load="lazy") */
protected $metadata;
}
Для того, чтобы атрибуты заработали на вашем проекте, просто обновите пакет cycle/annotated
минимум до версии 2.3
.
По умолчанию в генераторах схемы будет настроен
SelectiveReader
,
обеспечивающий парсинг одновременно аннотаций и атрибутов.
Вы можете переопределить SelectiveReader
в генераторах в пользу, например,
AnnotationReader
или
AttributeReader
,
если вам нужно использовать только один источник данных.
Список генераторов, принимающих ReaderInterface
:
\Cycle\Annotated\Embeddings
\Cycle\Annotated\Entities
\Cycle\Annotated\MergeColumns
\Cycle\Annotated\MergeIndexes