https://github.com/bpolaszek/doctrine-changeset
https://github.com/bpolaszek/doctrine-changeset
Last synced: 11 months ago
JSON representation
- Host: GitHub
- URL: https://github.com/bpolaszek/doctrine-changeset
- Owner: bpolaszek
- License: mit
- Created: 2023-10-13T10:09:17.000Z (about 2 years ago)
- Default Branch: main
- Last Pushed: 2023-12-09T15:28:47.000Z (about 2 years ago)
- Last Synced: 2025-02-10T15:17:09.854Z (11 months ago)
- Language: PHP
- Size: 66.4 KB
- Stars: 0
- Watchers: 2
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
[](https://github.com/bpolaszek/doctrine-changeset/actions/workflows/ci.yml)
[](https://codecov.io/gh/bpolaszek/doctrine-changeset)
# Doctrine Changes Tracker
This package provides an `EntityTracker` service for your Doctrine entities.
This service allows you to easily track changes made to an entity, i.e.
```php
$entity->name = 'foo';
$tracker->hasChanged($entity); // true
$tracker->hasChanged($entity, 'name'); // true
$changeSet=$tracker->getChangeSet($entity, 'name');
$changeSet->from; // Previous value
$changeSet->to; // New value
$changeSet->hadPreviousValue('foo'); // false
$changeSet->hasNewValue('bar'); // false
$changeSet->hasChangedFor(null, 'foo'); // true
$changeSet->hadPreviousValue(whatever()->except(null)); // false
$changeSet->hasNewValue(oneOf('foo', 'bar')); // true
```
This package also provides a `#[TrackChanges]` attributes on properties typed as `object` -
this allows Doctrine to be aware on changes on nested objects (which isn't the case by default, unless you assign a different object).
## Usage
Just inject `EntityTracker` in your services and use the helper methods.
### Example:
```php
title = 'PHP For Dummiez';
$book->isbn = '00000000001';
assert(true === $this->tracker->hasChanged($book));
$this->em->persist($book);
$this->em->flush();
}
public function updateBook(): void
{
$repository = $this->em->getRepository(Book::class)
$book = $repository->findOneBy(['isbn' => '00000000001']);
$book->title = 'PHP For Dummies';
assert(true === $this->tracker->hasChanged($book));
assert(true === $this->tracker->hasChanged($book, 'title'));
assert(false === $this->tracker->hasChanged($book, 'isbn'));
assert(true === $this->tracker->getChangeSet($book, 'title')->hadPreviousValue('PHP For Dummiez'));
assert(true === $this->tracker->getChangeSet($book, 'title')->hasNewValue('PHP For Dummies'));
// Shorthand for both methods above
assert(true === $this->tracker->getChangeSet($book, 'title')->hasChangedFor('PHP For Dummiez', 'PHP For Dummies'));
// You can also check for multiple values
assert(true === $this->tracker->getChangeSet($book, 'title')->hadPreviousValue(oneOf('PHP For Dummies', 'PHP For Dummiez')));
assert(true === $this->tracker->getChangeSet($book, 'title')->hasNewValue(whatever()->except(null, 'PHP For Dummiez')));
$this->em->flush();
}
}
```
### Track object changes
By default, Doctrine doesn't track changes on embedded objects. For example:
```php
namespace App\Entity;
use DateTimeImmutable;
use Doctrine\ORM\Mapping as ORM;
use Doctrine\DBAL\Types\Types;
#[ORM\Entity]
class Book
{
#[ORM\Id, ORM\Column, ORM\GeneratedValue]
public int $id;
#[ORM\Column]
public string $title;
#[ORM\Column(type: Types::OBJECT)]
public object $data;
}
```
Doing this:
```php
$book = $repository->findOneBy([])
$book->data->foo = 'bar'
$em->flush(); // Will have no effect as soon as no other scalar or array property has been changed
```
To enforce Doctrine track changes on embedded objects, simply add the `TrackChanges` attribute.
```php
namespace App\Entity;
use BenTools\DoctrineChangeSet\Tracker\TrackChanges;
// ...
#[ORM\Entity]
class Book
{
// ...
#[ORM\Column(type: Types::OBJECT)]
#[TrackChanges]
public object $data;
}
```
## Installation
```shell
composer require bentools/doctrine-changeset
```
Then, add the following line to your `bundles.php`:
```php
# config/bundles.php
return [
// ...
BenTools\DoctrineChangeSet\Bundle\DoctrineChangeSetBundle::class => ['all' => true],
];
```
## Tests
```shell
composer ci:check
```
## License
MIT.