<?php
/**
 * Copyright © 2013-2017 Magento, Inc. All rights reserved.
 * See COPYING.txt for license details.
 */
namespace Magento\Catalog\Model\ResourceModel\Product;

/**
 * Catalog Product Relations Resource model
 *
 * @author      Magento Core Team <core@magentocommerce.com>
 */
class Relation extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
    /**
     * Initialize resource model and define main table
     *
     * @return void
     */
    protected function _construct()
    {
        $this->_init('catalog_product_relation', 'parent_id');
    }

    /**
     * Save (rebuild) product relations
     *
     * @param int $parentId
     * @param array $childIds
     * @return $this
     */
    public function processRelations($parentId, $childIds)
    {
        $select = $this->getConnection()->select()->from(
            $this->getMainTable(),
            ['child_id']
        )->where(
            'parent_id = ?',
            $parentId
        );
        $old = $this->getConnection()->fetchCol($select);
        $new = $childIds;

        $insert = array_diff($new, $old);
        $delete = array_diff($old, $new);

        $this->addRelations($parentId, $insert);
        $this->removeRelations($parentId, $delete);

        return $this;
    }

    /**
     * Add Relations
     *
     * @param int $parentId
     * @param int[] $childIds
     * @return $this
     * @throws \Magento\Framework\Exception\LocalizedException
     */
    public function addRelations($parentId, $childIds)
    {
        if (!empty($childIds)) {
            $insertData = [];
            foreach ($childIds as $childId) {
                $insertData[] = ['parent_id' => $parentId, 'child_id' => $childId];
            }
            $this->getConnection()->insertMultiple($this->getMainTable(), $insertData);
        }
        return $this;
    }

    /**
     * Remove Relations
     *
     * @param int $parentId
     * @param int[] $childIds
     * @return $this
     * @throws \Magento\Framework\Exception\LocalizedException
     */
    public function removeRelations($parentId, $childIds)
    {
        if (!empty($childIds)) {
            $where = join(
                ' AND ',
                [
                    $this->getConnection()->quoteInto('parent_id = ?', $parentId),
                    $this->getConnection()->quoteInto('child_id IN(?)', $childIds)
                ]
            );
            $this->getConnection()->delete($this->getMainTable(), $where);
        }
        return $this;
    }
}
