Remove specific field from model before creating after processing laravel - php

I am trying to make a trait for storing images for models. I am not able to remove the thumbnail from the model.
Is there any way to remove the thumbnail field from the model because there is no field like a thumbnail in the table?
trait ModelHelpers
{
protected static $thumbnail;
public static function boot()
{
parent::boot();
self::creating(function($model){
$collection = collect($model);
self::$thumbnail = $collection->only('thumbnail');
$collection->except(['thumbnail']);
$model->ignoreField('thumbnail');
// ... code here
});
}
}
OR
Is there any way to add the data in the model that don't process while mysql query but is available in the model for processing before or after creating?
Right now I am adding the thumbnail key in fillable to get into the model but it is processed while the insert query that i don't want to:
protected $fillable = ['user_id', 'title', 'meta_title', 'slug', 'summary', 'published','published_time', 'thumbnail'];

$fillbale is used to define the properties you want to use in inserting.
If you want to skip some properties to insert it, you must use $guarded

Related

How to sync if model id is hidden field?

I'm trying to sync data to pivot table for my model. But my Recipe model has an hidden id field. Like this;
protected $hidden = ['id', 'content', 'difficulty_id'];
And when I try to sync relationships to pivot table, recipe_id becomes zero. If I remove id from $hidden above, it sync id without any problem. I also tried to call makeVisible("id") for the model but didn't help.
$changedMeals = $record->meals()->sync($meals);
How can I sync id when keeping it in $hidden?
Thank you very much...
currently, im using pivot with $hidden in primary, and foreign not in pivot, im using sync($request->field_to_sync) and im using validator to validate ids, and it worked
eg:
class Recipe ...
{
protected $hidden = ['id'];
public function meals(){
return $this->belongsToMany(Pivot::class);
}
}
class Meals ...
{
protected $hidden = ['id'];
public function recipe(){
return $this->belongsToMany(Pivot::class);
}
}
so i assume u are using sync() in your code without using Request::input(), you can try this :
$meals = Meals::select('id')->get()
->map(function($value, $key){
return $value->setVisible(['id']);
});
then u can use sync() like this :
Recipe::find(1)->meals()->sync($meals);

Laravel Update or Create Relationships

I have an Item model, that has ItemTranslations, I'm receive a Request with the Item I'm updating and the translations for that Item.
Now some of those translations will already be in the database (they have their own id), and some of them will be new. Is there a clean way to go about this?
In pseudo: Update the Item with this request, for each Translations you find in this request, update the translation relation if it exists, else create it for this Item.
This is the layout of my Item.
class Item extends Model
{
protected $fillable = ['menu_id', 'parent_id', 'title', 'order', 'resource_link', 'html_class', 'is_blank'];
public function translations()
{
return $this->hasMany(MenuItemTranslation::class, 'menu_item_id');
}
}
This is the ItemTranslation
class ItemTranslation extends Model
{
protected $table = 'item_translations';
protected $fillable = ['menu_item_id', 'locale', 'name', 'order', 'description', 'link', 'is_online'];
}
You could use the updateOrCreate method on the translations() relationship. For example:
$item->translations()->updateOrCreate([
'name' => $translation['name'],
// Fields that should be used to find an existing record.
], [
'description' => "New description",
// Fields that should be updated.
]);
The first argument is the data that you want Eloquent to look up the translation by and second argument is the data that you want to be updated.
Both arguments will be used to create a new translation when an existing one couldn't be found.

Laravel fill column value with default value while saving

I want to fill the token field in users table with value while saving data to table.
How to achieve both in query builder and eloquent.
You can use the Model events adding a boot method into Model class like this.
public static function boot()
{
parent::boot();
static::created(function ($model) {
$model->token = str_random(40);
});
}
Also you can create an observer to do the same and then to add the protected $dispatchesEvents array into the model.

Accessing Eloquent relationship attributes

I have three models all related by one-to-many. Category, Subcategory and Style. I have relationships working both ways - though I seem to have a problem accessing related attributes.
After my queries have ran, I'm left with this an instance of Style where 'relations' is an instance of Subcategory, and 'relations' in Subcategory is an instance of Category. Which is all correct.
The problem is that I now seem to not be able to access the related model instances. For example, if I call:
$style->subcategory->name;
I get 'Trying to get property of non-object'. So I tried calling just $style->subcategory and the result is '1'.
Why doesn't $style->subcategory return the instance of the subcategory model? Am I missing something or is my understanding incorrect?
--EDIT--
Models
Category
<?php
namespace Paragon\Products;
use Illuminate\Database\Eloquent\Model as Eloquent;
class Category extends Eloquent {
protected $table = 'product_categories';
protected $fillable = [
'name',
'slug',
'image'
];
public function subcategories() {
return $this->hasMany('Paragon\Products\Subcategory', 'category');
}
}
Subcategory
<?php
namespace Paragon\Products;
use Illuminate\Database\Eloquent\Model as Eloquent;
class Subcategory extends Eloquent {
protected $table = 'product_subcategories';
protected $fillable = [
'category',
'name',
'slug',
'image'
];
public function styles() {
return $this->hasMany('Paragon\Products\Style', 'subcategory');
}
public function category() {
return $this->belongsTo('Paragon\Products\Category', 'category');
}
}
Style
<?php
namespace Paragon\Products;
use Illuminate\Database\Eloquent\Model as Eloquent;
class Style extends Eloquent {
protected $table = 'product_styles';
protected $fillable = [
'subcategory',
'name',
'slug',
'image'
];
public function subcategory() {
return $this->belongsTo('Paragon\Products\Subcategory', 'subcategory');
}
}
Query
$style->where($id, $item)->with('subcategory.category')->first();
Tables
Paragon\Products\Category
ID ...
1
2
Paragon\Products\Subcategory
ID Category ...
1 2
2 2
Paragon\Products\Style
ID Subcategory ...
1 1
2 1
Since the subcategory method in the Style model should refer to a single instance of Subcategory and not a Collection of them, shouldn't I be able to just call attributes the way I am (or am trying to)?
Ok I think I see now what is going on. Your Eloquent model is called subcategory, but so is the foreign key. So when you call
$style->subcategory
That is returning the foreign key instead of the model. To fix this, I'd recommend changing the name of the foreign key id to subcategory_id. If you can't change the database, you could force it to use the model by chaining the method with something like this
$style->subcategory()->first()->name
Edit:
Another idea, you could change the name of the relationship to something like
public function subcategory_item()
{
return $this->belongsTo('Paragon\Products\Subcategory', 'subcategory');
}
Then you ought to be able to properly reference it with
$style->subcategory_item->name
I am taking a shot in the dark here. But I will try and explain how to work with collection and difference between first and get.
$users= $user-> with('images') -> first(); <-- this is first row in the table users, each user has many images.
$users-> username; //works;
$users-> images-> image_name; // wont work , model has many ,
you get error <-- Trying to get property of non-object.
// access the proprety image and loop through the collection of objects.
$images = $user-> images; //
foreach ($images as $image){
echo $image- >image_name;
}
on the other hand if the image did belong to one user and the user has one image. You can access image_name like this
$user -> image(() -> image_name;
in your case
$style -> subcategory() -> name;
to get a style by id with subcategoty
$style -> with('subcategry') -> where('id', $styleId) -> first();

Laravel Eloquent Save to DB Using Create - Unhelpful Error

I get a very unhelpful error when I try and insert a new record in to my db. Does anyone have any idea where to start to solve this error?
user_id
That's all it says. (This is the name of one of my required fields in the table I'm saving to but it's not very descriptive.)
For reference here's my code:
$data = array(
'user_id'=>1,
'post_type'=>'0',
'post_title'=>'blah',
'description'=>'blah');
//it fails on this line
$id = Post::create($data);
Here's what my model looks like:
class Post extends Eloquent{
public static $rules = array(
'user_id'=>'required',
'post_type'=>'required',
'post_title' => 'required|max:25',
'description'=>'required'
);
public static function validate($data){
return Validator::make($data, static::$rules);
}
public function user(){
return $this->hasOne('User', 'id', 'user_id');
}
}
Tried getting rid of all relationships and validation in the model. That didn't work.
This is called mass-assignment in Laravel, what you need to do to get it working on your model is to set a protected array called $guarded to be empty. Add this to your model.
protected $guarded = array();
What this array does, it can prevent attributes to be mass-assigned with an array, if you don't want an attribute to be filled with the Model::create() method, then you need to specify that attribute in the $guarded array.
If instead you want to specify only the fillable attributes, Laravel's Eloquent also provides an array called $fillable where you specify only the attributes that you want to fill via the mass-assigment way.
Further reading:
Mass Assignment:
http://laravel.com/docs/eloquent#mass-assignment
Create Method:
http://laravel.com/docs/eloquent#insert-update-delete

Categories