Pergunta

I have the following class written for PHP 5.4.x. Should this work as I expect?

class SqlBuilder {
    private $dbTable;
    private $action;
    private $data;
    private $clause;

    public function toString() {
        // $sql = generate sql string
        // [...]
        return $sql;
    }

    [...]

    public function setClause($clause) {
        $this->clause = $clause;
    }

    public function setDbTable($dbTable) {
        $this->dbTable = $dbTable;
    }   

    public function setAction($action) {
        $this->action = $action;
    }
}   
$sql = (new \dbal\SqlBuilder())
            ->setAction($this->action)
            ->setClause($this->clause)
            ->setDbTable($this->dbTable)
            ->toString();

I am expecting to be able to access all of my setter methods. Instead I see the following error:

Fatal error: Call to a member function toString() on a non-object )

This seems to work:

$builder= new \dbal\SqlBuilder();
$builder->setAction($this->action)
$builder->setClause($this->clause)
$builder->setDbTable($this->dbTable)
$sql = $builder->toString();

But I know that this works as well:

class Foo
{
    public $a = "I'm a!";
    public $b = "I'm b!";
    public $c;

    public function getB() {
        return $this->b;
    }

    public function setC($c) {
        $this->c = $c;
        return $this;
    }

    public function getC() {
        return $this->c;
    }
}

print (new Foo)
       ->setC($_GET["c"])
       ->getC(); // I'm c!

I've used this style of syntax in Javascript before. Is there a way to make it work in PHP?

Foi útil?

Solução

What you are asking about is called method chaining. In order for it to work the way you want, each method call needs to return a reference to the object that you are calling. So,

->setAction($this->action)
// needs to return $this; so that
        ->setClause($this->clause)
// knows what to operate upon and in turn needs to return $this; so that
        ->setDbTable($this->dbTable)
// can do the same

Try :

public function setClause($clause) {
    $this->clause = $clause;
    return $this;
}

public function setDbTable($dbTable) {
    $this->dbTable = $dbTable;
    return $this;
}   

public function setAction($action) {
    $this->action = $action;
    return $this;
}
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top