<?php
/**
 * @link http://www.yiiframework.com/
 * @copyright Copyright (c) 2008 Yii Software LLC
 * @license http://www.yiiframework.com/license/
 */

namespace yii\debug\components\search;

use yii\base\Component;
use yii\debug\components\search\matchers\MatcherInterface;

/**
 * Provides array filtering capabilities.
 *
 * @author Mark Jebri <mark.github@yandex.ru>
 * @since 2.0
 */
class Filter extends Component
{
	/**
	 * @var array rules for matching filters in the way: [:fieldName => [rule1, rule2,..]]
	 */
	protected $rules = [];

	/**
	 * Adds data filtering rule.
	 *
	 * @param string $name attribute name
	 * @param MatcherInterface $rule
	 */
	public function addMatcher($name, MatcherInterface $rule)
	{
		if ($rule->hasValue()) {
			$this->rules[$name][] = $rule;
		}
	}

	/**
	 * Applies filter on a given array and returns filtered data.
	 *
	 * @param array $data data to filter
	 * @return array filtered data
	 */
	public function filter(array $data)
	{
		$filtered = [];

		foreach ($data as $row) {
			if ($this->passesFilter($row)) {
				$filtered[] = $row;
			}
		}

		return $filtered;
	}

	/**
	 * Checks if the given data satisfies filters.
	 *
	 * @param array $row data
	 * @return boolean if data passed filtering
	 */
	private function passesFilter(array $row)
	{
		foreach ($row as $name => $value) {
			if (isset($this->rules[$name])) {
				// check all rules for a given attribute
				foreach ($this->rules[$name] as $rule) {
					/** @var MatcherInterface $rule */
					if (!$rule->match($value)) {
						return false;
					}
				}
			}
		}

		return true;
	}
}
