<?php
/**
 * SeekQuarry/Yioop --
 * Open Source Pure PHP Search Engine, Crawler, and Indexer
 *
 * Copyright (C) 2009 - 2026  Chris Pollett chris@pollett.org
 *
 * LICENSE:
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <https://www.gnu.org/licenses/>.
 *
 * END LICENSE
 *
 * @author Chris Pollett chris@pollett.org
 * @license https://www.gnu.org/licenses/ GPL3
 * @link https://www.seekquarry.com/
 * @copyright 2009 - 2026
 * @filesource
 */
namespace seekquarry\yioop\tests;

use seekquarry\yioop\controllers\components\SystemComponent;
use seekquarry\yioop\library\UnitTest;

/**
 * Stands in for the controller a component holds as its parent, giving
 * just the string cleaner the scope-selection rule calls.
 *
 * @author Chris Pollett
 */
class StubCleanController
{
    /**
     * Returns the value unchanged for the string type the scope rule
     * asks for, standing in for the controller's cleaner.
     *
     * @param mixed $value value to clean
     * @param string $type requested clean type
     * @return mixed the value as given
     */
    public function clean($value, $type)
    {
        return $value;
    }
}
/**
 * Stands in for the group model, giving just the route-domain list the
 * scope-selection rule matches the request host against.
 *
 * @author Chris Pollett
 */
class StubDomainGroupModel
{
    /**
     * Lists the configured route domains the scope rule matches the
     * request host against.
     *
     * @return array route domain names each mapped to a group name
     */
    public function getDomainRoutes()
    {
        return ["frise.org" => "G1", "example.com" => "G2"];
    }
}
/**
 * Unit tests for the appearance-domain scope selection in
 * SystemComponent, the rule that decides which domain the Appearance
 * activity opens on. With no explicit choice the scope follows the host
 * in the address bar when that host is a configured route domain, and is
 * the global scope otherwise; an explicit choice is honored when it names
 * a route domain and falls back to the global scope otherwise.
 *
 * @author Chris Pollett
 */
class SystemComponentTest extends UnitTest
{
    /**
     * @var object component under test
     */
    public $component;
    /**
     * @var object route-domain group model stub
     */
    public $group_model;
    /**
     * Builds a SystemComponent whose parent only needs to clean strings
     * and whose group model only needs to list the route domains, which
     * is all the scope-selection rule reads.
     */
    public function setUp()
    {
        $this->component = new SystemComponent(new StubCleanController());
        $this->group_model = new StubDomainGroupModel();
    }
    /**
     * Clears the request key the tests set so one test does not leak an
     * explicit choice into the next.
     */
    public function tearDown()
    {
        unset($_REQUEST['APPEARANCE_DOMAIN']);
    }
    /**
     * With no explicit choice, the scope is the current host when that
     * host is a route domain, the host port is ignored when matching,
     * and the scope is global when the host is not a route domain.
     */
    public function appearanceDomainDefaultsToHostTestCase()
    {
        unset($_REQUEST['APPEARANCE_DOMAIN']);
        $_SERVER['HTTP_HOST'] = "frise.org";
        $this->assertEqual(
            $this->component->appearanceDomain($this->group_model),
            "frise.org",
            "route host with no choice selects that domain");
        $_SERVER['HTTP_HOST'] = "frise.org:8080";
        $this->assertEqual(
            $this->component->appearanceDomain($this->group_model),
            "frise.org", "the host port is ignored when matching");
        $_SERVER['HTTP_HOST'] = "unlisted.test";
        $this->assertEqual(
            $this->component->appearanceDomain($this->group_model),
            "", "a non-route host with no choice is the global scope");
    }
    /**
     * An explicit choice is honored when it names a route domain; the
     * empty value and any non-route value are the global scope.
     */
    public function appearanceDomainHonorsExplicitChoiceTestCase()
    {
        $_SERVER['HTTP_HOST'] = "frise.org";
        $_REQUEST['APPEARANCE_DOMAIN'] = "example.com";
        $this->assertEqual(
            $this->component->appearanceDomain($this->group_model),
            "example.com", "an explicit route domain is honored");
        $_REQUEST['APPEARANCE_DOMAIN'] = "";
        $this->assertEqual(
            $this->component->appearanceDomain($this->group_model),
            "", "an explicit empty choice is the global scope");
        $_REQUEST['APPEARANCE_DOMAIN'] = "bad.test";
        $this->assertEqual(
            $this->component->appearanceDomain($this->group_model),
            "", "an explicit non-route choice is the global scope");
    }
}
