Caco Caco - 3 months ago 15
PHP Question

PHP constructor generates infinite loop when call method inside method

I have a constructor in Laravel Eloquent Model. When I instantiate the Model I've got an infinite loop when the method that constructor calls call another method.

class ChessboardCell extends Model
{
//...

public function __construct()
{
parent::__construct();

//...

$this->putPieces('pawn', 'black', $blackPawns);

//...
}

private function putPieces($piece, $player, $piecesArray)
{
//...

if ($piece == 'pawn') {
for ($file = 'a'; $file <= 'h'; $file++) {
$pawnPiece = array_shift($piecesArray);
$this->putPieceOnBoard($file, $rank, $pawnPiece);
}
}

//...
}

public function putPieceOnBoard($file, $rank, $piece)
{
$chessboardCell = ChessboardCell::where('file', $file)
->where('rank', $rank)
->first();

if (is_null($chessboardCell)) {
// Gera excessão: não pegou a célula
}
$chessboardCell->current_piece = $piece->id;

$chessboardCell->save();
}

}


After calling
$this->putPieceOnBoard
inside
putPieces function
gets infinite loop.

What happens here?

Answer

First of all notice that this piece of code calls you constructor:

    $chessboardCell = ChessboardCell::where('file', $file)
        ->where('rank', $rank)
        ->first();

Then notice that you are calling putPieces() from the __constructor() and the __constructor() is called by the putPieceOnBoard() which is called by putPieces() and so on and so forth.

So the solution in this case is the holy principle of Single Responsibility (here), you remove the putPieces() from the constructor and call it separately instead.

For more about the software design principles please check this