I'm trying to define a custom create method in my Image model to upload the file to storage and give it a unique file name.
I can't seem to find anything since 5.4 about the procedure to create the custom method. I've checked the docs and I (think I) am doing it as they say. See https://laravel.com/docs/5.4/upgrade "The create & forceCreate Methods".
My model:
protected $fillable = [
'name',
'caption',
'path'
];
public static function create(array $attributes, $image, $extension, $folder = null)
{
die("It died.");
$attributes['path'] = FileNameGenerator::getNewFilePath($extension);
Storage::disk('s3')->put( $folder . $attributes['path'], File::get($image));
$model = static::query()->create($attributes);
return $model;
}
Where I'm calling the model:
Auth::user()->image()->create([], $image, $extension, config('app.profile_pictures_path'));
I'm getting an error that path doesn't have a default value.
It's as if the method is being completely ignored as the die method isn't called. I've also tried changing the function's parameters to look exactly like what is shown in the docs but that still yields the same result.
Apologies if this is a newbie question. I really can't see anything wrong.
Related
this is my laravel custom accessor which I am appending using
protected $appends = [leave_balances];
public function getLeaveBalancesAttribute() {
// some code
}
I want to pass a parameter when I am calling this accessor like this
public function getLeaveBalancesAttribute($parameter) {
// use $parameter here
}
$payslip = Payslip::find(1);
\Log::debug($payslip->leave_balances("PARAMETER"));
I have searched and found that it is not possible. please can some one provide any solution to this I need to pass this parameter.
you dont append attribute unless you want it to act as an attribute,
you can just create a method since you are calling it like a method
in you Payslip model
public function leaveBalances( $params ) {
return $params
}
then you can use it like
$payslip = Payslip::find(1);
$payslip->leaveBalances("PARAMETER") // which output PARAMETER
If you declare an Attribute, you can only use it like this (following your example:
protected $appends = ['leave_balances'];
public function getLeaveBalancesAttribute()
{
return 'Hi!';
}
$payslip = Payslip::find(1);
$value = $payslip->leave_balances;
dd($value); // This will output string(Hi!)
What you (I think) want is setLeaveBalancesAttribute, so you can pass a value and do whatever you want with it:
public function setLeaveBalancesAttribute($parameter)
{
return $parameter.' Yes!';
}
$payslip = Payslip::find(1);
$payslip->leave_balances = 'It works!';
dd($payslip->leave_balances); // This will output string(It works! Yes!)
But, if you are using Laravel 9+, please do use the new way of defining attributes, it is better.
You can set the attribute $appends in the model where you have the accessor. Something like this:
protected $appends = ['the name of accessor'];
However, it will be in the most, I think in all, the responses or query you do with the model you declare it.
Another options is creating a single instance of the model using the ::find method. For example:
$model_instance = Model::find($id);
$attribute = $model_instance->attribute;
Here is the documentation reference: https://laravel.com/docs/9.x/eloquent-mutators#defining-an-accessor
I want to pass current user's id into a column by default. I tried giving it in the migration but didn't work, this code did work when I pass an integer but it gives an error when I try to set it to Auth::id()
Code I've tried (in the model file)
protected $attributes = [
'employee_id' => Auth::id(),
];
Error I get :
Constant expression contains invalid operations
It does work when I give it a hard coded string or integer value. But I need to give it the current user's id.
Not sure if it's really a good idea, but you can add this in your Model
protected static function booted()
{
static::creating(function ($model) {
$model->employee_id = Auth::id();
});
}
Check the docs for the complete list of event.
https://laravel.com/docs/9.x/eloquent#events-using-closures
I have downloaded an open source accounting script from akaunting.com. This source code is developed in Laravel. I am trying to add one more field in the items table, but I am not able to find the insert statement in this script.
Here is the controller code. After this I am not getting any idea.
public function store(Request $request)
{
$item = Item::create($request->input());
// Upload picture
if ($request->file('picture')) {
$media = $this->getMedia($request->file('picture'), 'items');
$item->attachMedia($media, 'picture');
}
$message = trans('messages.success.added', ['type' => trans_choice('general.items', 1)]);
flash($message)->success();
return redirect()->route('items.index');
}
After a long search I got the solution.
In app/models/common/item.php we can add extra fields. The text box name and database column name should be the same.
protected $fillable = ['company_id', 'name', 'sku', 'description', 'sale_price', 'purchase_price', 'quantity', 'category_id', 'tax_id', 'enabled','expiry_date'];
I have seen the similar Q asked here but did not find any suitable answer and hence asking again. If you know any thread please guide me to it,
I have
Model User and Model Property and both have Address
class Address {
protected $fillable = ['address','city','state','zip'];
public function addressable(){
return $this->morphTo();
}
}//Address
class User extends Eloquent {
protected $fillable = ['first_name','last_name', 'title'];
public function address(){
return $this->morphMany('Address', 'addressable');
}
}//User
class Property extends Eloquent {
protected $fillable = ['name','code'];
public function address(){
return $this->morphMany('Address', 'addressable');
}
}//Property
Is there any way to UpdateIfNotCreate type method for address to update as well associate with User/Property?
Taylor Otwell's official answer,
$account = Account::find(99);
User::find(1)->account()->associate($account)->save();
is NOT working as I am getting an exception
message: "Call to undefined method Illuminate\Database\Query\Builder::associate()"
type: "BadMethodCallException"
The way I have solved the issue is as follows:
$data = Input::all();
if($data['id'] > 0){
$address_id = $data['id']; unset($data['id']);
$address = Address::find($address_id)->update($data);
}//existing
else{
$address = new Address($data);
User::find($user_id)->address()->save($address);
}//add new
I could use the different Routes ( PUT to /update{id} and POST to / )
but in my case both new and existing records are coming to same route ( /update )
Can you guys please recommend the better way to go about this?
Thx,
It's pretty straightforward:
// get only applicable fields
$input = Input::only('address','city','state','zip');
// get existing or instantiate new address
$address = Address::firstOrNew($input);
// associate the address with the user
// btw I would rather call this relation addresses if it's morhpmany
User::find($userId)->addresses()->save($address);
Not sure where you got Taylor's answer, but I don't think it was supposed for this case. It couldn't work anyway.
Im a big 'ol newbie at Laravel, and im trying to do a query scope but it doesnt seem to be working, i keep getting this error
Argument 1 passed to Letters::scopeForUser() must be an instance of User
My user IS logged in, but it still doesnt seem to be working.
This is my Letters model
<?php
class Letters extends Eloquent {
protected $table = 'letters';
public function scopeForUser(User $u)
{
return $query->where('userid', '=', $u->id);
}
}
and in my controller i have the following
Route::get('myletters', array(
'before' => 'auth|userdetail',
function()
{
// Grab the letters, if any, for this user
$letters = Letters::forUser(Auth::user())->get();
$data = [
'letters' => $letters
];
return View::make('myletters', $data);
}
));
Any help would be greatly appreciated.
Cheers
You should pass a variable $query as the first argument to your method in the Model. For example:
public function scopeForUser($query, User $u)
{
return $query->where('userid', '=', $u->id);
}
The first argument doesn't necessarily need to be $query, but it should be the same variable that you are using inside the scope method ($query in this case).