public function delete()
{
/**
* Check for many2many attributes and make sure related Entity has a corresponding many2many attribute defined.
* If not - deleting is not allowed.
*/
/* @var $attr Many2ManyAttribute */
$thisClass = get_class($this);
foreach ($this->getAttributes() as $attrName => $attr) {
if ($this->isInstanceOf($attr, AttributeType::MANY2MANY)) {
$foundMatch = false;
$relatedClass = $attr->getEntity();
$relatedEntity = new $relatedClass();
/* @var $relAttr Many2ManyAttribute */
foreach ($relatedEntity->getAttributes() as $relAttr) {
if ($this->isInstanceOf($relAttr, AttributeType::MANY2MANY) && $this->isInstanceOf($this, $relAttr->getEntity())) {
$foundMatch = true;
}
}
if (!$foundMatch) {
throw new EntityException(EntityException::NO_MATCHING_MANY2MANY_ATTRIBUTE_FOUND, [$thisClass, $relatedClass, $attrName]);
}
}
}
/**
* First check all one2many records to see if deletion is restricted
*/
$one2manyDelete = [];
$many2oneDelete = [];
$many2manyDelete = [];
foreach ($this->getAttributes() as $key => $attr) {
if ($this->isInstanceOf($attr, AttributeType::ONE2MANY)) {
/* @var $attr One2ManyAttribute */
if ($attr->getOnDelete() == 'restrict' && $this->getAttribute($key)->getValue()->count() > 0) {
throw new EntityException(EntityException::ENTITY_DELETION_RESTRICTED, [$key]);
}
$one2manyDelete[] = $attr;
}
if ($this->isInstanceOf($attr, AttributeType::MANY2ONE) && $attr->getOnDelete() === 'cascade') {
$many2oneDelete[] = $attr;
}
if ($this->isInstanceOf($attr, AttributeType::MANY2MANY)) {
$many2manyDelete[] = $attr;
}
}
/**
* Delete one2many records
*/
foreach ($one2manyDelete as $attr) {
foreach ($attr->getValue() as $item) {
$item->delete();
}
}
/**
* Delete many2many records
*/
foreach ($many2manyDelete as $attr) {
$attr->unlinkAll();
}
/**
* Delete many2one records that are set to 'cascade'
*/
foreach ($many2oneDelete as $attr) {
$value = $attr->getValue();
if ($value && $value instanceof AbstractEntity) {
$value->delete();
}
}
/**
* Delete $this
*/
$this->entity()->getDatabase()->delete(static::$entityCollection, ['_id' => $this->entity()->getDatabase()->id($this->id)]);
static::entity()->remove($this);
return true;
}