I'm using MannikJ/laravel-sti but the following code has a different behaviour in tinker and in a controller (assuming the definitions in larevel-sti's documentation, with classes Root, Sub1 and Sub2):
Root::find(1234)
In tinker, it correctly returns an instance of Sub1. But in a controller, it returns null.
I get the correct instance in the controller if I replace the code with:
Sub1::find(1234)
Thanks to the maintainer (cf. issue #1), we found that the problem is that we use constructors in our objects but laravel-sti's trait also does. Constructors are a known issue in PHP with traits…
Related
Can someone explain the difference between $model->attributesToArray() and $model->toArray() on a model?
I have an issue where a seeder is throwing an error about getCreatedAtAttribute method is not defined and it's complaining due to a toArray() method call. This is what prompted me to try and find out the difference between the two.
After switching to attributesToArray() the seeder runs fine.
attributesToArray will only fetch the attributes for the current model.
toArray calls the attributesToArray function, but also adds loaded relations to the array.
I'm developing a Laravel 5 package where I have a "Member" model which currently extends App\User model. I would like to know the best practice to let any developer use a custom "Member" model instead of the one from the package. This is for example to allow a developer use another table.
One approach that seems to work without having done a deep test with it is to make an alias in my package service provider in the register() method:
$MemberModel = 'MyVendor\MyPackage\Member';
$loader = \Illuminate\Foundation\AliasLoader::getInstance();
$loader->alias('MyMember', $MemberModel);
In this case I have to:
Replace all entries in the code from the original class to the alias
Delete all php "use" entries related to it
Get the value of $MemberModel from a config file or the database
But I don't know if it is a good way to solve it or It may cause any conflict.
Is there any other and better approach for this goal? Thanks in advance!
I finally had to test by myself this approach without haven't read the solution anywhere else, but anyway everything seems to work fine in my source code.
If anyone is looking for doing anything similar, the code example in my question works because the $MemberModel is defined with a value. If you want to get that value from a Model instance, as me, you have to add that code in the boot() method of the service provider.
This question already has answers here:
Troubleshooting referencing a model in a laravel controller
(2 answers)
Closed 6 years ago.
I'm finding the distinction between "Controller" and "Model" in laravel 5.2 to be very blurry.
I use artisan to create a RESTful controller, and in the store method, I try to create a new object.
// store in the database
$car = new App\Models\CarModel;
Then I get the error as follows:
Class 'carfreak\Http\Controllers\App\Models\CarModel' not found
So it all seems to come down to the namespace of the controller, but I don't understand it.
The name space describes the controller, right?
So why is my reference the model, being built on the controllers path? It shouldn't have anything to do with it... right?
EDIT: After trying various suggestions, I've concluded there are three things to look at:
Each class has a namespace set, correctly describing the folder where the class is located
In the controller, have the statement "Use app\models\CarModel"
refer to the model in the controller.
Each seems to be correct, but I still get the error that it cannot find the model
This is a namespace problem in php.
You just use like this.
$car = new \App\Models\CarModel;
or
use App\Models\CarModel;
....
class {
$car = new CarModel;
}
First of all check name space in Model file , Define name space in model file
namespace App\Http\Models;
And then use
use App\Http\Models\CarModel;
Well, here it is. I solved it by asking myself this question: If I'm having so much trouble namespacing, referencing and organising my models, then maybe I can get artisan to do it for me.
The post that got me thinking differently was Mansoor Akhtar's advice here: How do I instruct artisan to save model to specific directory?
Get artisan to make the model in the right place first time.
php artisan make:model Models/CarModel
In the Controller, reference the model correctly
use name-of-app\Models\CarModel;
There may or may not be cache flushing involved in my problem. I was eventially restarting my XAMPP after every change to ensure no caching was involved. I also tried
php artisan cache:clear
You'll need to add a use statement to the top of your class.
Try:
use carfreak\Models\CarModel;
class ...
This assumes that your model is in the carfreak\Models namespace, and in a Models folder within your App / carfreak folder, otherwise you'll just need use carfreak\CarModel;.
I believe you have just ran the artisan command to create the model and you didn't move the CarModel file to Models folder. (Correct me if I'm wrong)
So in your controller add this before class declaration:
use carfreak\CarModel;
Then anywhere in your controller you can access the model like this:
$car = new CarModel;
I try to upgrade from Laravel 3 to 4 but i get this error everywhere
Call to undefined method
Illuminate\Database\Query\Builder::getAfterFilters()
Someone know where this can come ?
I had this error too so I'll just post my observations here. It can always help someone !
It appears that getAfterFilters() is a method that is required for all controllers in L4.
If the error says it's not defined, you probably forgot to extend BaseController in your class.
Knowing that, the obvious fix would be to extend BaseController... but you don't nececarly have to if it's not needed.
In my case, my class had to be a valid controller because of a very stupid reason. I was using the following route syntax :
Route::get('sse', 'SSE#deamon');
SSE was not extending BaseController (didn't need to imho)
But this route syntax requires you to use a controller class that extends BaseController... so I changed it for:
Route::get('sse', [function() {
SSE::deamon();
}]);
and it now works without the missing getAfterFilters() error !
Okay, Here is one more thing that might happen...
the method you are running on your controller might not be defined correctly in the route... for example, this is what I did myself:
Route::get('vendors/getData', 'Vendors#getData');
Route::resource("vendors","VendorsController");
which should have been
Route::get('vendors/getData', 'VendorsController#getData');
Route::resource("vendors","VendorsController");
instead! So basically what Amaud said is perfect! my getData function was not extending base controller as I tried running the function of the model instead of the controller! You might want to check that out before pulling your hair out!
I had the same problem. In routes.php, I missed out the Controller word.
My mistake
Route::get('/list-users/{status?}/{page?}', 'User#listUsers');
Should be
Route::get('/list-users/{status?}/{page?}', 'UserController#listUsers');
I have been trying to use BLToolkit to activate an Oracle stored procedure which takes a User Defined Type as an argument as an output parameter and changes it.
I have managed to do this on a primitive type, and and also by manually calling SetSpCommamd however I would like to use the abstract class generation method but can't seem to get it to work.
I'm pretty sure the code I wrote is correct (works for the primitive). When debugging I found the SetSpCommamd called by the generated code gets wierd parameters instead of the ones I provided as opposed to when I call the method manually (the it gets the exact parameters I'd like). I wish I could see the code generated by the reflection emit to see what's wrong there.
Can anyone please help me figure out why this is not working?
Found the problem (Potentially a bug in BLToolkit).
BLToolkit does not pass the UDT Class as is to the procedure (instead it tries to flatten it or something and pass the insides of the object). I Changed the object to a Struct instead of a Class and that fixed it.
Later on I also changed it back to class and made a patch in the 'IsScaler()' method in BLToolkits code.
I will report this as a Bug I hope they fix it.