【问题标题】:Load a PHP class multiple times多次加载一个 PHP 类
【发布时间】:2017-10-18 09:39:40
【问题描述】:

我创建了一个具有多个私有、公共函数和构造函数的类。它是一个连接到 vCloud API 的客户端。我想要两个加载了这个类的不同启动的对象。它们必须并行存在。

$vcloud1 = new vCloud(0, 'system');
$vcloud2 = new vCloud(211, 'org');

当我检查$vcloud1 的输出时,它加载了$vcloud2 的信息。这是正确的,应该发生这种情况吗?知道如何多次加载一个类并隔离两个类加载吗?

这是我的课程的一部分,它拥有最重要的功能。使用要登录的用户和组织构造。如果数据库中的信息存在,那么我们使用数据库信息进行身份验证,否则我们使用系统级凭据进行身份验证。所以我想要两个类加载,一个是用户级登录,一个是系统级登录。

class vCloud {
    private $client;
    private $session_id;
    private $sdk_ver = '7.0'; 
    private $system_user = 'xxxxxxxxxxx';
    private $system_password = 'xxxxxxxxxxxxxxxxx';
    private $system_host = 'xxxxxxxxxxxxx';
    private $org_user;
    private $org_password;
    private $org_host;
    private $base_url;

    public function __construct($customerId, $orgName) {

        if ($this->vcloud_get_db_info($customerId)) {
            $this->base_url = 'https://' . $this->org_host . '/api/';
            $this->base_user = $this->org_user . "@" . $orgName;
            $this->base_password = $this->org_password;
        } else {
            $this->base_url = 'https://' . $this->system_host . '/api/';
            $this->base_user = $this->system_user;
            $this->base_password = $this->system_password;
        }

        $response = \Httpful\Request::post($this->base_url . 'sessions')
            ->addHeaders([
                'Accept' => 'application/*+xml;version=' . $this->sdk_ver
            ])
            ->authenticateWith($this->base_user, $this->base_password)
            ->send();

        $this->client = Httpful\Request::init()
            ->addHeaders([
                'Accept' => 'application/*+xml;version=' . $this->sdk_ver,
                'x-vcloud-authorization' => $response->headers['x-vcloud-authorization']
            ]);

        Httpful\Request::ini($this->client);
    }

    public function __destruct() {
        $deleted = $this->vcloud_delete_session();
        if (!$deleted) {
            echo "vCloud API session could not be deleted. Contact administrator if you see this message.";
        }
    }

    private function vcloud_delete_session() {
        if (isset($this->client)) {
            $response = $this->client::delete($this->base_url . 'session')->send();

            return $response->code == 204;
        } else {
            return FALSE;
        }
    }

    public function vcloud_get_db_info($customerId) {
        global $db_handle;

        $result = $db_handle->runQuery("SELECT * from vdc WHERE customer=" . $customerId);

        if ($result) {
            foreach ($result as $row) {
                if ($row['org_host'] != "") {
                    $this->org_user = $row['org_user'];
                    $this->org_password = $row['org_password'];
                    $this->org_host = $row['org_host'];
                    return true;
                } else {
                    return false;
                }
            }
        } else {
            return false;
        }
    }

    public function vcloud_get_admin_orgs() {
        $response = $this->client::get($this->base_url . 'query?type=organization&sortAsc=name&pageSize=100')->send();

        return $response->body;
    }
}

【问题讨论】:

  • 你告诉我们......我们不知道类vCloud的定义是什么
  • 可以发一下vcloud的内容吗?您的实例化似乎正确
  • 请提供您班级的一些代码 sn-p 可以帮助我们了解问题到底是什么。
  • "SELECT * from vdc WHERE customer=" . $customerId.... 您的 customerIds 是字符串值('user1''user2'),因此您正在执行的 SQL 无效.... 请学会使用带有绑定变量的预处理语句
  • 第一个参数是一个整数,我已经编辑了我的例子。 SQL 查询有效。

标签: php function class


【解决方案1】:
$vcloud1 = new vCloud('user1', 'system');
$vcloud2 = new vCloud('user2', 'org');

这足以产生两个不相关的实例。

我想您的数据库正在返回相同的结果。

【讨论】:

  • 不,不是这样。我将它深入到我用来获取 XML 信息的 httpful 客户端。当我在每个 $vcloudX 之后转储它的信息时,我得到相同的结果,而在我的班级中,我设置了不同的变量。我想我需要在 __destruct 处重置 httpful,对吗?
  • 这可能是它。我没用过Httpful
  • 两个 $vcloud 的输出都以 object(vCloud)#2 (10) { ["client":"vCloud":private]=> object(Httpful\Request)#12 (22) 开头。这表明客户端在两个 $vcloud 之间共享。我需要找到一种方法来隔离两个客户端。欢迎任何帮助。
  • 我已经向开发者 github 网站发布了同样的问题:link
【解决方案2】:

如何为每个检索 vCloud 实例的对象提供自定义 equals 方法?

class vCloud {
  //Other definitions

  public function equals(vCloud $other){
    //Return true if $other is same as this class (has same client_id etc etc)
  }
}

所以你只需要按照代码说的做:

$vcloud1 = new vCloud('user1', 'system');
$vcloud2 = new vCloud('user2', 'org');

if($vcloud1.equals($vclous2)){
 echo "Entries are the same";
} else {
 echo "Entries are NOT the same";
}

此外,您可能需要在类定义中加入各种 getter 和 setter 方法。你需要做的是填写equals方法。

【讨论】:

    猜你喜欢
    • 2012-01-20
    • 2011-12-31
    • 2011-01-14
    • 2011-04-15
    • 2010-09-18
    • 2023-03-28
    • 1970-01-01
    • 2011-04-12
    • 2016-10-25
    相关资源
    最近更新 更多