<?php
namespace ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Interfaces\ClientInterface;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap\Actions\Account;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap\Actions\ClassOfServices;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap\Actions\Server;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap\Actions\DistributionList;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap\Actions\Domain;
use ModulesGarden\Servers\ZimbraEmail\App\Libs\Zimbra\Components\Api\Soap\Actions\User;
use ModulesGarden\Servers\ZimbraEmail\App\Traits\StorageTrait;
use MySoapClient;
use SoapFault;
use SoapHeader;
use SoapParam;
use SoapVar;

/**
 *
 * Created by PhpStorm.
 * User: Tomasz Bielecki ( tomasz.bi@modulesgarden.com )
 * Date: 27.08.19
 * Time: 15:39
 * Class SoapClient
 * @property Account $account
 * @property DistributionList $distributionList
 * @property Domain $domain
 * @property User $user
 * @property ClassOfServices $classOfServices
 * @property Server $server
 * @property Connection $connection
 *
 */
class Client implements ClientInterface
{
    use StorageTrait;

    /**
     * @var Connection
     */
    protected $connection;

    /**
     * @var Repository
     */
    protected $repository;

    /**
     * @var Services
     */
    protected $service;

    /**
     * Client constructor.
     * @param $server
     * @param int $port
     * @param $username
     * @param $password
     * @param string $user
     * @throws SoapFault
     */
    public function __construct($server, $port = 7071, $username, $password, $user = "admin")
    {
        $this->connection = new Connection($server, $port, $username, $password, $user);
        $this->connection->login();
    }

    /**
     * @param $conection
     */
    public function setConnection($conection)
    {
        $this->connection = $conection;
    }

    /**
     * @return Connection
     */
    public function getConnection()
    {
        return $this->connection;
    }

    /**
     *
     * return repository manager
     * @return Repository
     */
    public function repository()
    {
        if(!$this->repository)
        {
            $this->repository = new Repository($this);
        }

        return $this->repository;
    }

    /**
     * @return Services
     */
    public function service()
    {
        if(!$this->service)
        {
            $this->service = new Services($this);
        }
        return $this->service;
    }

    /**
     * @param $name
     * @return mixed
     * @throws \Exception
     */
    public function __get($name)
    {
        if(!$this->getStorage()->exists(strtolower($name)))
        {
            $class = '\\ModulesGarden\\Servers\\ZimbraEmail\\App\\Libs\\Zimbra\\Components\\Api\\Soap\\Actions\\'.ucfirst($name);

            if(!class_exists($class))
            {
                throw new \Exception('Action class '.$class.' does not exists');
            }

            $action = new $class($this->connection);

            $this->getStorage()->set(strtolower($name), $action);
        }else{

            $action = $this->getStorage()->get(strtolower($name));
        }

        return $action;
    }
}