Models in laravel - laravel

I'm developing an app in laravel, specifically a social network.
After wasting some time stuck on an issue I found out I had two files wich responded to the user model.
One is namespaced under "appname" and the other under "appname\Models",
Adding the posts() method in the one under "appname" gave me an error where the method couldn't be found, so I assumed the one under "appname\Models" was the correct one. Although deleting the "User.php" under "appname" gives me a
Fatal error: Class 'Instyle\User' not found
error.
I'm sure I've misunderstood something along the lines I just can't point out where.
app\Models\User.php
namespace Instyle\Models;
use Illuminate\Foundation\Auth\User as Authenticatable;
class User extends Authenticatable
{
protected $table = 'users';
protected $fillable = [
'username',
'email',
'password',
'first_name',
'last_name',
'location',
];
protected $hidden = [
'password',
'remember_token',
];
public function getName()
{
if($this->first_name && $this->last_name)
{
return "{$this->first_name} {$this->last_name}";
}
if ($this->first_name)
{
return $this->first_name;
}
return null;
}
public function getUsername()
{
return $this->username;
}
public function getFirstNameOrUsername()
{
return $this->first_name ?: $this->username;
}
public function getAvatarUrl()
{
$hash = md5(strtolower(trim($this->attributes['email'])));
return "http://www.gravatar.com/avatar/$hash?d=https://u.pomf.is/maqope.png";
}
public function posts()
{
return $this->hasMany('Instyle\Post');
}
}
app/User.php
<?php
namespace Instyle;
use Illuminate\Foundation\Auth\User as Authenticatable;
class User extends Authenticatable
{
protected $fillable = [
'name', 'email', 'password',
];
protected $hidden = [
'password', 'remember_token',
];
public function posts()
{
return $this->hasMany('Instyle\Post');
}
}
app\post.php
<?php
namespace Instyle;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Database\Eloquent\Model;
class Post extends Model
{
protected $fillable = ['body'];
// protected $appends = ['humanCreatedAt'];
public function user()
{
return $this->belongsTo('Instyle\User');
}
}

if your application name is Instyle, Instyle\User is the User.php inside the app folder not the User.php in app/Models/.
More info: learn more in psr namespacing and autoloading. check your compose.json . here it says that namespace Instyle is app/ folder and from here the namespace at the top of each file goes according to the absolute folder path.
"psr-4": {
"Instyle\\": "app/"
}
One more thing, If you are willing to use User.php anywhere else and thinking it for authentication purpose remember to change authentication configuration declared in config/auth.php accordingly

I would avoid to have both models with the same name because it may collide one with the other, although they are in different paths.
Make sure you are importing your custom models with the use path\to\your\namespace\Model; expression to allow the root path of your models to be located in a correct way.
May be helpful to see your Post and User models sample code to evaluate the error.
UPDATE: Why don't you try to generate only one User model and, the other data related with the User Profile, try to save in one One-to-One Relationship to a Profile table? i.e. firstname, lastname, location, twitter_account, facebook_account, phone_number, and so on could be stored in a User_Profile or Profile separated table, then you maintain your User table with the minimum required fields and delete the other one.

Related

Problem with laravel relationships (many to many + one to many), cant access them for some reason

so, i have this database
one "user" has many "inputs" and "input" has only one "habitos" and "sentimentos", so we can say that one user has many "habitos", and "sentimentos" too.
and i should be able to do something like {{$user->inputs->habitos}}, but for some reason i can't, and somehow {{$users->input}} works and {{$input->habitos}} also works, here is the code
user model:
class User extends Authenticatable
{
use HasApiTokens, HasFactory, Notifiable;
/**
* The attributes that are mass assignable.
*
* #var array<int, string>
*/
protected $fillable = [
'name',
'email',
'password',
'telefone',
'hotmart_id'
];
/**
* The attributes that should be hidden for serialization.
*
* #var array<int, string>
*/
protected $hidden = [
'password',
'remember_token',
];
/**
* The attributes that should be cast.
*
* #var array<string, string>
*/
protected $casts = [
'email_verified_at' => 'datetime',
];
public function input(){
return $this->hasmany(Input::class, 'user_id', 'id');
}
}
input model:
class Input extends Model
{
use HasFactory;
public function habito(){
return $this->belongsto(Habito::class, 'habito_id', 'id');
}
public function sentimento(){
return $this->belongsto(Sentimento::class, 'sentimento_id', 'id');
}
public function user(){
return $this->belongsto(User::class, 'user_id', 'id');
}
}
habito model:
class Habito extends Model
{
use HasFactory;
protected $fillable = ['nome', 'categoria'];
public function input(){
return $this->hasmany(Input::class, 'habito_id', 'id');
}
}
i've been searching for someone with the same problem, but i cant seem to find nothing on this, thanks in advance :).
I had the same issue, well.. almost the same.
I had Meals that has a pivot table with tags - so it's a many to many relationship and tags have a translation.
Picture this, when fetching the data and you use a query "with=tags", you actually fetch tagtranslations based on the Locale (en, de, fr, etc.), so you go through "meal_tag" pivot table, through "tag" table and finally you get to "tagtranslations" and fetch translations of the tag_id connected to the meal.
I don't think you have to use has
This is how I did it:
Meal Class:
public function tags(){
return $this->belongsToMany(Tag::class, 'meal_tags')->withTrashed();
}
MealTag class:
public function meals()
{
$this->hasMany(Meal::class, 'meal_id')->withTrashed();
}
public function tags()
{
$this->hasMany(Tag::class, 'tag_id')->withTrashed();
}
Tag class:
public function meals()
{
return $this->belongsToMany(Meal::class, 'meal_tags')->withTrashed();
}
public function translations()
{
return $this->hasOne(TagTranslation::class)->where('locale', app()->getLocale())->withTrashed();
}
**ignore the middleware for translations because you don't need it, just use withTrashed if you use softDeletes
and finally TagTranslations class:
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
use Staudenmeir\EloquentHasManyDeep\HasRelationships;
class TagTranslation extends Model
{
use HasFactory, SoftDeletes, HasRelationships;
public function tag(){
return $this->belongsTo(Tag::class)->withTrashed();
}
public function meals(){
return $this->hasManyDeep(Meal::class, [Tag::class, 'tag_id','meal_id'])->withTrashed;
}
}
notice I'm using hasManyDeep, for that you have to install staudenmeir package:
Click here to view on github
.. but the thing is, Eloquent should recognize everything you need even without hasManyDeep, but if it works like that, who am I to argue :D
this worked for me - if something goes wrong I'm sure it's just a matter of some slight adjustment.

Laravel 6.2 whereHasMorph not returning expected value

Need some help for laravel polymorphic. I'm trying to filter from the main table which is Comment to get its morph tables and search for the key word FOO. I have tried with whereHas but get error saying to use whereHasMorph so I tried changing whereHas to whereHasMorph. But every time i filter, the result will be an empty collection even if the value exist in the table. So I went through laravel documentation and found the below sample. I tried the sample but I'm still getting an empty collection. I have tried reading but could not find a fix.
Below is the sample code which I have tried
** Models **
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Comment extends Model
{
protected $table = 'comments';
protected $fillable = [
'body',
'commentable_id',
'commentable_type'
];
public function commentable()
{
return $this->morphTo();
}
}
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Post extends Model
{
protected $table = 'posts';
protected $fillable = [
'title',
'body'
];
public function comments()
{
return $this->morphMany('App\Comment', 'commentable');
}
}
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Video extends Model
{
protected $table = 'videos';
protected $fillable = [
'title',
'url'
];
public function comments()
{
return $this->morphMany('App\Comment', 'commentable');
}
}
** Controller **
public function commentList () {
$comments = App\Comment::whereHasMorph(
'commentable',
['App\Post', 'App\Video'],
function ($query) {
$query->where('title', 'like', '%foo%');
}
)->get();
dd($comments);
}
Is there anything I'm missing out or do i need to configure something or install some packages ?
"php": "^7.2",
"laravel/framework": "^6.2",
Images of DB table
I have tried and dont know why suddenly work when i remove the first \ in the DB.
Changed \App\Post in the table to App\Post and also in the code then it work already. Thanks for all the help.

insert data to table pivot use form and show it index.blade.php in laravel 5.7

I have form create team.blade.php below this
Form Team index.blade.php
display the name of the one-team user with that user, and display the project that is being done by the user, and display the user as what (role).
the relationship of one user has many teams. and one team has many users. therefore, I choose many to many relations. but when I create team, I want to insert user_id and team_id in the pivot user_teams table as the relation table between user and team.
but when I tried to create team failed, he did not save data to the user_teams table.
and in the team index, he does not display the name of a team user with that user, and displays the project that is being done by the user, and displays the user as what.
my user models
<?php
namespace App;
use Illuminate\Notifications\Notifiable;
use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Foundation\Auth\User as Authenticatable;
use App\Presence;
use App\Models\Project;
use App\Productivity;
use App\Sick_leave;
use App\Annual_leave;
use App\Models\Team;
class User extends Authenticatable
{
use Notifiable;
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'name', 'email', 'password', 'role_id',
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
public function role()
{
return $this->belongsTo(Role::class, 'role_id');
}
public function teams()
{
return $this->belongsToMany(Team::class, 'user_teams');
}
public function projects()
{
return $this->belongsToMany(Project::Class, 'user_projects');
}
}
Team Models
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
use App\User;
use App\Role;
use Auth;
class Team extends Model
{
use SoftDeletes;
protected $table = 'teams';
protected $fillable = [
'id',
'project_id',
];
public function users()
{
return $this->belongsToMany(User::class, 'user_teams');
}
public function project()
{
return $this->belongsTo(Project::class);
}
public function role()
{
return $this->belongsTo(Role::class);
}
}
Project Model
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
class Project extends Model
{
use SoftDeletes;
protected $table = 'projects';
protected $fillable = [
'project_id',
'project_name',
'start_date',
'end_date',
'project_category',
];
public function users()
{
return $this->belongsToMany(User::class, 'user_projects');
}
public function team()
{
return $this->hasOne(Team::class);
}
}
UserTeam model
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
class UserTeam extends Model
{
use SoftDeletes;
protected $table = "user_teams";
public function team()
{
return $this->belongsTo(Team::class);
}
public function user()
{
return $this->belongsTo(User::class);
}
}
Team Controller
public function index()
{
$users = auth()->user()->name;
$users = User::all();
return view ('teams.index', compact ('teams', 'users', 'projects'));
}
public function create()
{
$users = User::all();
$projects = Project::pluck('project_name', 'id');
return view ('teams.form', compact('projects', 'users'));
}
public function store(Request $request)
{
$team = Team::create($request->all());
$userIds = User::find(2);
$team->users()->attach($userIds);
return redirect()->route('team.create');
}
In user_teams has fields user_id and team_id. how do i overcome this??
You have to create the team and then attach the users that belong to it.
Example from the docs:
Attaching
Eloquent also provides a few additional helper methods to make working
with related models more convenient. For example, let's imagine a user
can have many roles and a role can have many users. To attach a role
to a user by inserting a record in the intermediate table that joins
the models, use the attach method:
$user = App\User::find(1);
$user->roles()->attach($roleId);
In your case:
Team Controller
public function store(Request $request)
{
$team = Team::create($request->except('user_id'));
$team->users()->attach($request->get('user_id', []));
return redirect()->route('team.create');
}

ORM not working in Default UserController & User Model in laravel

I want to get User wise Role. here is I'm facing error ....
UserController.php ( user controller file )
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Http\Requests\UserRequest;
use App\Employee;
use App\Role;
use App\User;
use App\Site;
use App\Client;
use App\ProjectType;
use App\UserPermission;
use Auth;
use DB;
use App\Project;
class UsersController extends BaseController {
public function __construct() {
$this->isSetClientAndProjectType();
$data = User::with('Role')->first();
echo "<pre>";print_r(json_decode($data)); die;
}
}
User.php ( user model file )
namespace App;
use Illuminate\Notifications\Notifiable;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Database\Eloquent\SoftDeletes;
class User extends Authenticatable {
use SoftDeletes;
use Notifiable;
protected $fillable = [
'name', 'role_id', 'password', 'siteid', 'email', 'status', 'allowed_to_bypass_pm', 'allowed_to_bypass_admin'
];
protected $hidden = [
'password', 'remember_token',
];
// Get users roles
public function Role() {
return $this->hasMany('App\Role', 'role_id', 'id');
}
}
Error is
How can i solve this error?
Help me guys.
Thank You.
If a user has many "roles" it should be public function roles().
You have defined:
A single user has a role_id
Therefore you need:
If a user has a single role it would be:
public function role() {
return $this->belongsTo('App\Role');
}
The reverse on the Role model would be:
public function users() {
return $this->belongsToMany('App\User');
}
Since many users can have the same role.
Hope this helps.
You need to add belongsTo relationship
namespace App;
use Illuminate\Notifications\Notifiable;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Database\Eloquent\SoftDeletes;
class User extends Authenticatable {
use SoftDeletes, Notifiable;
protected $fillable = [
'name', 'role_id', 'password', 'siteid', 'email', 'status', 'allowed_to_bypass_pm', 'allowed_to_bypass_admin'
];
protected $hidden = [
'password', 'remember_token',
];
// Get user's role
public function role() {
return $this->belongsTo('App\Role');
}
}
Now fetch data
$user = User::with('role')->find(1);
$role = $user->role;
You need to make sure your table structure and foreign key references are compatible with the model relationship methods used.
For example, you have used "HasMany" relationship on User model. For that, you will have to make sure that each record/row in users table(User model) "has many" associated records/rows in roles table(Role model).
Here HasMany method assumes a foreign key "role_id" on roles table(Role Model). On not finding of which, it throws error.
You first need to take in consideration the table structure of roles and users table(User and Role model) as per your requirement, and than add model relationship methods accordingly.
It can be a bit tricky if you are using the methods for the first time, you can refer the laravel documentation for the same:
eloquent-relationships

Eloquent Model has parent model

I have a Model called User with stuff like name, country and some relationships.
Now I want a Model, e.g. Vendor, having all the same functions and variables as a User including some More stuff
I thought I could to it this was:
class User extends Model implements AuthenticatableContract
{
use Authenticatable; SoftDeletes;
protected $dates = ['deleted_at', 'last_login'];
protected $fillable = [
'name',
'password',
'country',
];
protected $hidden = ['password'];
public function logs()
{
return $this->hasMany('App\Log');
}
}
And the Vendor Model:
class Vendor extends User
{
protected $fillable = [
'description'
];
public function user() {
return $this->belongsTo('App\User');
}
public function products()
{
return $this->hasMany('App\Product', 'vendor_id');
}
The Controller checks the role of the user and loads a user model or a vendor model:
if(Auth::user()->role > 1)
$user = Vendor::where('user_id', Auth::user()->id)->first();
else
$user = Auth::user();
return $user->load('logs');
But the load call fails for a vendor. I was able to join the fields of a user inside a vendor but I also need the functions of it.
The problem was that the logs function checks a field that doesn't exists.
Using this functions works:
public function logs()
{
return $this->hasMany('App\Log', 'user_id', get_called_class() !== get_class() ? 'user_id' : 'id');
}

Resources