4

以. login()_class Account

class Account {
 /* Class variables */

    public function login() {
        if(isset($_POST['username']) && isset($_POST['password']))
            return $this->_formLogin();
        else if(isset($_SESSION['accountId']))
            return $this->_sessionLogin();
        else if(isset($_COOKIE['username']) && isset($_COOKIE['password']))
            return $this->_cookieLogin();
        else return false;
    }

    private function _formLogin() {
        //perform login actions using $_POST data
    }
    /* All that other stuff */
}

试着暂时忽略对数据清理、密码加盐等看不见的方法的任何担忧。专注于login(),这个全球访问是坏juju吗?我通常避免在类中使用 PHP 超级全局变量,但我想不出在这种情况下不这样做的充分理由。

我可以理解为什么您不希望在跨类交互的全局变量中出现后台魔术,但是这些全局变量是内置在 PHP 中的,不会被类修改,并且仅由此类使用。

这将导致在您需要用户登录的页面的开头:

$user = new Account($whatever, $objects, $we, $depend, $on);
if($user->login()) {
    //Do this stuff when logged in
}

而不是在每个页面上都这样做,其逻辑可能需要稍后更改:

$user = new Account($whatever, $objects, $we, $depend, $on);
if(isset($_POST['username']) && isset($_POST['password']))
    $user->formLogin($_POST['username'], $_POST['password']);
else if(isset($_SESSION['accountId']))
    $user->sessionLogin($_SESSION['accountId']);
else if(isset($_COOKIE['username']) && isset($_COOKIE['password']))
    $user->cookieLogin($_COOKIE['username'], $_COOKIE['password']);
if($user->isLoggedIn() {
    //Do this stuff when logged in
}

虽然我知道在类之外创建一个函数来处理它是一种选择,但这不会和在类中混淆全局变量一样糟糕吗?

4

4 回答 4

7

要回答我自己的问题,我会说是的,只要您不修改它们以跨多个类访问它们,就可以访问超级全局变量。后台没有什么魔法——你只是在读取状态,超级全局变量是 PHP 为你提供的。

但是,您永远不应该修改类中的全局变量并在其他地方访问它。那是您使单元测试变得不可能的时候。

于 2009-04-12T23:17:01.503 回答
7

我不会说对这个问题有一个直接的是或否的答案。这个想法(所有 superglobals $_GET $_POST $_SESSION)是您要求的数据位于整个应用程序中,而不是您要求的范围内的数据。

这些超全局变量可能发生的情况是,如果它们在执行函数之前或(上帝保佑)期间由于某种原因而发生变化会怎样。这可能是一个非常烦人的错误重现。

所以我会说这是不好的形式。

于 2009-04-12T23:35:37.857 回答
2

一种方法是将所有超全局变量包装到自己的类中。我很确定 Zend Framework 有一个自己的类,例如操作 Cookie。

于 2009-04-12T23:31:21.050 回答
0

我会说这取决于您的应用程序的设计。如果该类是一些通用的、松散耦合的类或模块,并且突然使用了这样的全局变量,那么在我的书中那将是不好的做法。但是,如果该类显然面向特定任务,无论如何都需要这些特定的全局变量(例如您的登录示例),我看不到任何明确的反对意见。

于 2009-04-12T23:15:25.953 回答