5

Issue: Converting my Laravel 4 code to Laravel 5.2. I'm at the point of moving and converting my views and cannot get past the following error.

Error: ErrorException in IndexController.php line 27: Attempt to assign property of non-object

Debug Information:

  1. in IndexController.php line 27
  2. at HandleExceptions->handleError('2', 'Attempt to assign property of non-object', 'C:\Apache24\B2B_Contracts\app\Http\Controllers\IndexController.php', '27', array('numberofpcs' => object(additionalPCs), 'addtpcs' => array('0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '10', '11', '12', '13', '14', '15', '16', '17', '18', '19', '20', '21', '22', '23', '24', '25', '26', '27', '28', '29', '30', '31', '32', '33', '34', '35', '36', '37', '38', '39', '40', '41', '42', '43', '44', '45', '46', '47', '48', '49', '50', '51', '52', '53', '54', '55', '56', '57', '58', '59', '60', '61', '62', '63', '64', '65', '66', '67', '68', '69', '70', '71', '72', '73', '74', '75', '76', '77', '78', '79', '80', '81', '82', '83', '84', '85', '86', '87', '88', '89', '90', '91', '92', '93', '94', '95', '96', '97', '98', '99', '100'))) in IndexController.php line 27
  3. at IndexController->index()

Request: Please assist in figuring out why the error comes up and please explain in detail how to prevent it and what I am doing wrong with example, if possible.

Notes: I used to receive a similar error on Laravel 4 after I would seed the database but I was able to refresh the migrations and reseed the database and everything would start working again. This does not work with this error in Laravel 5. This code works on L4.

Attempts: I have been reading a lot on Google and have tried various items such as php artisan clear-compiled, composer dump-autoload, php artisan optimize to no avail. I believe the error is coming from $numberofpcs = new additionalPCs(); however I have not been able to confirm that. I have also removed all of the variables I am sending to the view and the error still persisted so it looked like $this->layout->content = View::make('index');

IndexController.php

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Library\additionalPCs;
use App\Http\Requests;
use App\Http\Controllers\Controller;
use View;
use App\Models\businesstype;
use App\Models\contractterm;


class IndexController extends BaseController
{
    Protected $layout = 'master';
    /**
     * Display a listing of the resource.
     *
     * @return Response
     */
    public function index()
    {
        /** Wayne - 03-02-2014 - Moved for loop to a method within its own class. */
        $numberofpcs = new additionalPCs();
        $addtpcs=$numberofpcs->display();
        $this->layout->content = View::make('index')->with('addtpcs', $addtpcs)->with('businesstypelist', businesstype::dropdown())->with('contracttermlist',ContractTerm::dropdown());
    }
}

additionalPCs.php

<?php
namespace App\Library;

use App\Library\additionalComputer;

class additionalPCs extends additionalComputer {
    public function display() {
        return $this->displayMenu();    
    }
}

additionalComputer.php

<?php
namespace App\Library;
/** Counts up the Number of Additional PC Options
* and stores them into an array then sends them to the view.
*/
    class additionalComputer {
        protected function displayMenu() {
            $addtpcs= [];
            for ($i=0; $i <= 100; $i++) {
            $addtpcs[$i] = $i;
            }
        return $addtpcs;
        }

    }

BaseController.php - (This is only here to show that I do have a BaseController.php file for the IndexController. I'm aware that L5 doesn't come with one by default.)

<?php
namespace App\Http\Controllers;

class BaseController extends Controller {

    /**
     * Setup the layout used by the controller.
     *
     * @return void
     */
    protected function setupLayout()
    {
        if ( ! is_null($this->layout))
        {
            $this->layout = View::make($this->layout);
        }
    }

}
scrfix
  • 1,188
  • 3
  • 11
  • 24

2 Answers2

1

The controller layout functionality was removed in Laravel 5. Because of this, the setupLayout() method is not getting called, meaning your layout property is staying as just the string 'master'. Since it is just a string, when you do $this->layout->content = ..., you're attempting to assign a property of a non-object.

I believe you should be able to add this back in if you want. In your BaseController, you will need to override the callAction method to the way it used to be:

public function callAction($method, $parameters)
{
    $this->setupLayout();

    $response = call_user_func_array(array($this, $method), $parameters);

    // If no response is returned from the controller action and a layout is being
    // used we will assume we want to just return the layout view as any nested
    // views were probably bound on this view during this controller actions.

    if (is_null($response) && ! is_null($this->layout)) {
        $response = $this->layout;
    }

    return $response;
}
patricus
  • 59,488
  • 15
  • 143
  • 145
  • I added that code to the BaseController however I received the following error: FatalErrorException in IndexController.php line 3: Namespace declaration statement has to be the very first statement or after any declare call in the script. I tried to move the namespace App\Http\Controllers; to right after – scrfix Jan 28 '16 at 14:20
  • Thank you for letting me know that L5 doesn't support controller layout functionality anymore. How should I be doing this then? return view('greeting')->with('name', 'Victoria'); as taken from here: https://laravel.com/docs/5.2/views#basic-usage - Can I do that from the controller or is returning any views from the controller removed as well? – scrfix Jan 28 '16 at 14:26
  • It took me a little bit but it appears that I can change $this->layout->content = View::make('index')->with('addtpcs', $addtpcs)->with('businesstypelist', businesstype::dropdown())->with('contracttermlist',ContractTerm::dropdown()); to return view('index')->with('addtpcs', $addtpcs)->with('businesstypelist', businesstype::dropdown())->with('contracttermlist',ContractTerm::dropdown()); and that gets me to my next error. I cannot mark the above as a correct response because there is still an error when I use the above so anyone else that runs into this will end up with the same error using it. – scrfix Jan 28 '16 at 18:19
1

Patricus assisted me with finding this answer but I wanted to post this because the answer provided still had issues when I attempted it. He was correct however in that I could no longer utilize Controller Layouts.

I changed

$this->layout->content = View::make('index')->with('addtpcs', $addtpcs)->with('businesstypelist', businesstype::dropdown())->with('contracttermlist',ContractTerm::dropdown());

to

return view('index')->with('addtpcs', $addtpcs)->with('businesstypelist', businesstype::dropdown())->with('contracttermlist',ContractTerm::dropdown()); 

This resolved that issue.

scrfix
  • 1,188
  • 3
  • 11
  • 24