I'm producing an online school platform and in part of it student can see it's classes with their informations..but the related function return this error : Undefined offset: 0 (View: C:\xampp\htdocs\OnlineSchool\resources\views\admin\student\ClassReport.blade.php)
there are some relations between models
My Models:
USER(students and teachers) ، LEVEL(level of classes) ، Classroom.
=> there is a many to many relation between student and classroom (pivot table)
please save me from this stupid error
user:
class User extends Authenticatable
{
use Notifiable;
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'name', 'email', 'password','image','level','code_meli',
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
/**
* The attributes that should be cast to native types.
*
* #var array
*/
protected $casts = [
'email_verified_at' => 'datetime',
];
public function classroom(){
return $this->hasMany (classroom::class);
}
public function ClassRoomStudent(){
return $this->belongsToMany (classroom::class ,'classroom_user','user_id','classroom_id');
}
}
classroom:
class classroom extends Model
{
protected $fillable = [
'title', 'teacher_id', 'level_id','day','time','price',
];
public function Student(){
return $this->belongsToMany (user::class ,'classroom_user','classroom_id','user_id');
}
public function level(){
return $this->belongsTo (level::class );
}
public function teacher(){
return $this->belongsTo (user::class );
}
}
level :
class level extends Model
{
protected $fillable = [
'title',
];
public function classroom(){
return $this->hasMany (classroom::class);
}
public function exam(){
return $this->hasMany (exam::class);
}
}
and my function in controller:
public function MyClasses(){
$student_id=auth ()->user ()->id;
$classrooms=classroom::with ('level','teacher','factor')->wherehas('student',function ($q) use($student_id){
$q->where('id',$student_id);
})->get();
return view ('admin.student.ClassReport',compact ('classrooms','student_id'));
}
at the end .. my blade:
#foreach($classrooms as $class)
<tr>
<td>{{$i++}}</td>
<td>{{$class->title}}</td>
<td>{{$class->teacher[0]->name}}</td>
.
.
.
.
</tr>
#endforeach
The Classroom belongs to only one teacher, no need to use de zero index, just type $class->teacher->name
Related
I want to retrieve data using eloquent model and return it in the following json response.
user[
transactions[],
clients[
ubications[],
contactos[],
plans[],
]
]
Currently I am receiving user,transcation and clients data but I am not able to retreive the data inside client property e.g ubications[],contactos[] and plans[].So I need help regarding the sub properties as I have already implemented the relationship.
Here are the models I am using
User.php
class User extends Authenticatable
{
use Notifiable,HasApiTokens;
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'username', 'email', 'password',
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
/**
* The attributes that should be cast to native types.
*
* #var array
*/
protected $casts = [
'email_verified_at' => 'datetime',
];
public function token(){
return $this->access_token;
}
public function transaction(){
return $this->hasMany(Transaction::class);
}
public function plan(){
return $this->hasManyThrough(Plan::class,Client::class);
}
public function ubication(){
return $this->hasManyThrough(Ubicacion::class,Client::class);
}
public function contacto(){
return $this->hasManyThrough(Contacto::class,Client::class);
}
public function client(){
return $this->hasMany(Client::class);
}
}
Client.php
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Client extends Model
{
protected $fillable=[
'nombre',
'ruc',
'status',
'user_id'
];
public function contacto(){
return $this->hasMany(Contacto::class);
}
public function feedback(){
return $this->hasMany(Feedback::class);
}
public function plan(){
return $this->hasMany(Plan::class);
}
public function ubication(){
return $this->hasMany(Ubicacion::class);
}
public function user(){
return $this->belongsTo(User::class);
}
}
You can use nested data Eager Loading:
Laravel Documentation Eager Loading
$user = User::find(1)
->with('clients', 'clients.contacto', 'clients.ubications', 'clients.plans')
->get();
I have a user model which has a child relationship called teacher. How can I add a field from the related teacher model to the dataset returned of the parent user model?
I would like the user model returned to have a structure like below:
user.firstname
user.lastname
user.teacher.address
I have tried using the following and variations thereof with no success:
$query->select('firstname', 'lastname')
->addSelect( \DB::raw('teachers.address AS address') );
user.php model:
use Notifiable;
use SoftDeletes;
use EncryptableTrait;
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'title',
'firstname',
'firstname_h',
'lastname',
'lastname_h',
'email',
'email_h',
'password',
'userable_id',
'userable_type'
];
/**
* The attributes that are mass encryptable, using the EncryptableTrait.
*
* #var array
*/
protected $encryptable = [
'firstname',
'lastname',
'email',
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
public function userable()
{
return $this->morphTo();
}
public function teacher() // Using custom BelongsToMorph relationship type
{
return BelongsToMorph::build($this, Teacher::class, 'userable');
}
public function roles()
{
return $this->belongsToMany('App\Role')->withTimestamps();
}
public function schools()
{
return $this->belongsToMany('App\School')->withPivot('suspended', 'rating');
}
public function thisSchool()
{
return $this->belongsToMany('App\School')->where('school_id', Auth::user()->userable->id)->withPivot('id', 'suspended', 'rating', 'notes');
}
public function addRole($user, $role_id)
{
$user->roles()->attach($role_id);
}
public function removeRole($user, $role_id)
{
$user->roles()->detach($role_id);
}
public function isAdmin($user)
{
foreach ($user->roles as $role) {
if($role->id == 4) {
return true;
} else {
$return = false;
}
}
return $return;
}
public function isSchoolAdmin($user)
{
foreach ($user->roles as $role) {
if($role->id == 2) {
return true;
} else {
$return = false;
}
}
return $return;
}
public function events()
{
return $this->belongsToMany('App\Event')->withPivot('cancelled', 'cancelled_by');
}
public function devices()
{
return $this->hasMany('App\Device');
}
public function teachingstages()
{
return $this->belongsToMany('App\Teachingstage', 'teacher_teachingstage')->orderBy('teachingstage_id');
}
public function teachingsubjects()
{
return $this->belongsToMany('App\Teachingsubject', 'teacher_teachingsubject');
}
teacher.php model:
use EncryptableTrait;
protected $table = "teachers";
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'mobile',
'dob',
'gender',
'address',
'postcode',
'latitude',
'longitude',
'max_distance',
'public',
'photo',
'experience',
'active',
'verified',
'payscale',
'ta_number',
'temp_or_perm',
'locked'
];
/**
* The attributes that are mass encryptable, using the EncryptableTrait.
*
* #var array
*/
protected $encryptable = [
'mobile',
'address',
'postcode',
'experience',
'ta_number'
];
public function user()
{
return $this->morphOne('App\User', 'userable');
}
public function criterias()
{
return $this->hasMany('App\Criteria');
}
public function bookingrequests()
{
return $this->belongsToMany('App\Bookingrequest')->withPivot('sent', 'sent_at', 'declined', 'created_at', 'updated_at');
}
public function blacklist()
{
return $this->hasMany('App\Blacklist');
}
This is my existing query that I am having issues with:
$query = User::where('userable_type', 'App\Teacher');
$query->with('userable');
$query->select('firstname', 'lastname')
->addSelect( \DB::raw('teachers.address AS address') );
$query->whereDoesntHave('thisSchool');
$otherTeachers = $query->get();
This is an existing app and everything works as expected; my question is more about how I can add a child model column as an alias to the parent model (I will then use the new alias columns to calculate something).
Thanks in advance,
K...
OK, I worked this out myself in the end.
I added a scope to my user model:
public function scopeJoinWithTeacher($query)
{
return $query->leftJoin("teachers", "teachers.id", "=", "users.userable_id");
}
I then implemented this new scope in my query and aliased columns from child to parent model in the get():
$query = User::where('userable_type', 'App\Teacher');
$query->with('userable');
$query->whereDoesntHave('thisSchool');
$query->JoinWithTeacher();
$query->orderBy( 'distance', 'ASC' );
$otherTeachers = $query->get(['teachers.longitude AS longitude', 'teachers.latitude AS latitude', 'users.*']);
I now have the longitude and latitude columns from the teacher child relation in my parent model returned from eloquent. In my specific case, I then go further to use these alias fields to calculated distance and create a new alias called distance in my user model.
Hope that helps somebody who was attempting the same thing!
K...
Hi following are my relations
User Model
public function loginlogout()
{
$this->HasMany("App\Models\LoginLogoutLogs");
}
and this is my LoginLogoutLogs Model
public function users()
{
return $this->belongsTo('App\Models\User');
}
I am trying to access name from Users like this
$loginLogoutLogs = LoginLogoutLogs::all();
foreach($loginLogoutLogs as $loginLogoutLog){
dd($loginLogoutLog->users()->name);
}
but i am getting this error
Undefined property: Illuminate\Database\Eloquent\Relations\BelongsTo::$name
EDIT Adding Models
<?php
namespace App\Models;
use Illuminate\Notifications\Notifiable;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Zizaco\Entrust\Traits\EntrustUserTrait;
use Session;
use Illuminate\Support\Facades\DB;
class User extends Authenticatable
{
use Notifiable;
use EntrustUserTrait;
protected $table = 'tbl_users';
protected $primaryKey = 'id';
protected $guarded = ['id'];
const API = 'api';
const WEB = 'web';
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'name', 'email', 'password', 'last_login', 'Address', 'Age', 'DateOfBirth', 'created_by', 'deleted_by'
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
protected $casts = [
'is_admin' => 'boolean',
];
public function isAdmin()
{
return $this->is_admin;
}
static function GetUserNamebyID($id)
{
$name = User::select("name")->where(["id" => $id])->pluck('name');
if (isset($name[0])) {
return $name[0];
} else {
return '';
}
}
public function loginlogout()
{
$this->HasMany("App\Models\LoginLogoutLogs", 'userID');
}
public function company()
{
$this->HasMany("App\Models\Company");
}
}
And now LoginLogouts Model
<?php
namespace App\Models;
use Illuminate\Notifications\Notifiable;
use Zizaco\Entrust\Traits\EntrustUserTrait;
use Illuminate\Database\Eloquent\Model;
use Session;
use Illuminate\Support\Facades\DB;
class LoginLogoutLogs extends Model
{
use Notifiable;
use EntrustUserTrait;
protected $table = 'tbl_users_logs';
protected $primaryKey = 'id';
protected $guarded = ['id'];
const API = 'api';
const WEB = 'web';
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'userID','is_accpeted','type','addedFrom'
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
protected $casts = [
'is_admin' => 'boolean',
];
public function isAdmin()
{
return $this->is_admin;
}
// change company to hasmany
public function user()
{
return $this->belongsTo('App\Models\User');
}
}
simply change your part of
dd($loginLogoutLog->users()->name);
into
dd($loginLogoutLog->users->name);
remove the bracket on users, its the easy fix.
here we obtain a property, not a function.... (although in the model its defined as function)
Easy fix:
$loginLogoutLogs = LoginLogoutLogs::all();
foreach($loginLogoutLogs as $loginLogoutLog){
dd($loginLogoutLog->users->name);
}
You want to access the relationship entities, as opposed to the relationship model.
By using users(), your code thinks you are trying to call a name() method on the users model, as opposed to your users method on the LoginLogoutLogs class.
You need to change your relationship with user adding the foreign key in LoginLogoutLogs:
public function user()
{
return $this->belongsTo('App\Models\User', 'userID');
}
Also ensure that you call user insted of users
$loginLogoutLogs = LoginLogoutLogs::all();
foreach($loginLogoutLogs as $loginLogoutLog){
dd($loginLogoutLog->user->name);
}
And if you want to perform use eager loading:
$loginLogoutLogs = LoginLogoutLogs::with('user')->get();
foreach($loginLogoutLogs as $loginLogoutLog){
dd($loginLogoutLog->user->name);
}
Remove () when you are getting the child model and add a second parameter to belongsTo.
Here you are:
Migrations:
// Parent migration (create_clients_table):
Schema::create('clients', function (Blueprint $table) {
$table->unsignedBigInteger('user_id');
$table->foreign('user_id')
->references('id')
->on('users')
->onDelete('cascade');
});
// Child migration (create_payments_table):
Schema::create('payments', function (Blueprint $table) {
$table->unsignedBigInteger('client_id');
$table->foreign('client_id')
->references('id')
->on('clients')
->onDelete('cascade');
});
Models relationship:
// Child (Client Model)
public function owner()
{
return $this->belongsTo(User::class, 'user_id');
}
// Parent (User Model)
public function clients()
{
return $this->hasMany(Client::class);
}
Data output:
// Route:
Route::get('/client/{id}/payments', [PaymentController::class, 'paymentsOfClient']);
// In controller (PaymentController):
/**
* Display a listing of the payments of specified Client.
*
* #param string $id
* #return \Illuminate\Http\Response
*/
public function paymentsOfClient($id)
{
$client = Client::find($id);
// check permissions
if (auth()->user()->id !== $client->owner->id) {
return;
}
$payments = $client->payments()->paginate(20);
return response()->json($payments);
}
I am creating a user profile page and I want to retrieve the data from my User model and UserProfile model. But I have a problem in getting the result. Here's what I did:
User model
class User extends Authenticatable
{
use Notifiable;
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'name', 'email', 'password', 'username',
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
/*
public function isAdmin() {
return $this->admin;
}
*/
public function profile() {
return $this->hasOne('App\UserProfile');
}
}
UserProfile model
class UserProfile extends Model
{
protected $table = 'user_profile';
protected $fillable = [
'phone',
'address'
];
public function user() {
return $this->belongsTo('App\User');
}
}
Then I access the relation in my ProfileController
public function getProfile($username) {
$user = User::with('user_profile')->where('username', $username)->get();
dd($user);
}
And I got this error:
Call to undefined relationship [user_profile] on model [App\User].
The user_profile is my table name
Use proper relationship name:
$user = User::with('profile')->where('username', $username)->first();
Also, in this case you should use the first() method to get an user object.
I have a site running Laravel 4.2 that I am working on right now, the problem is that I have a single model for orders and another child model for items that belong to the order. The items also have a child model for size information and image information.
I have my query:
$orders = Auth::user()->orders()->with('items','items.size','items.image')->get()->toArray();
This returns what I am expecting, but I want to have the results paginated using Laravel's pagination. I had expected this to work:
$orders = Auth::user()->orders()->with('items','items.size','items.image')->paginate( 10 );
This returns a blank white page and a 500 error and for the life of me I can't figure out how to get this to work correctly.
Here are my various models: User.php
use Illuminate\Auth\UserTrait;
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableTrait;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface {
use UserTrait, RemindableTrait;
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('password', 'remember_token');
protected $fillable = array( 'first_name', 'last_name', 'address', 'city', 'state', 'zip', 'lat', 'lng', 'email', 'phone', 'password', 'hash', 'type', 'blocked', 'created_at', 'updated_at', 'deleted_at' );
public function setPasswordAttribute( $value ) {
return $this -> attributes['password'] = Hash::make( $value );
}
public function projects() {
return $this -> belongsToMany('Project');
}
public function orders() {
return $this->hasMany('PrintOrder');
}
public function bookings() {
return $this -> belongsToMany('Booking');
}
}
PrintOrder.php
use Illuminate\Database\Eloquent\SoftDeletingTrait;
class PrintOrder extends Eloquent {
use SoftDeletingTrait;
protected $dates = ['deleted_at'];
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'print_orders';
protected $fillable = array( 'project_id', 'user_id', 'status', 'created_at', 'updated_at', 'deleted_at' );
public function items() {
return $this->hasMany('PrintOrderItem');
}
}
PrintOrderItem.php
use Illuminate\Database\Eloquent\SoftDeletingTrait;
class PrintOrderItem extends Eloquent {
use SoftDeletingTrait;
protected $dates = ['deleted_at'];
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'print_order_items';
protected $fillable = array( 'print_order_id', 'upload_id', 'size_id', 'quantity', 'created_at', 'updated_at', 'deleted_at' );
public function image() {
return $this->hasOne('Upload','id');
}
public function size() {
return $this->hasOne('PrintSize', 'id');
}
}
Upload.php
use Illuminate\Database\Eloquent\SoftDeletingTrait;
class Upload extends Eloquent {
use SoftDeletingTrait;
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'uploads';
protected $fillable = array( 'user_id', 'project_id', 'thumbnail', 'small','medium','large','original','title', 'description','keywords', 'file_type','file_size','file_extension','created_at', 'updated_at', 'deleted_at' );
protected $dates = ['deleted_at'];
public function categories() {
return $this->belongsToMany('UploadCategory', 'upload_image_categorys');
}
}
PrintSize.php
use Illuminate\Database\Eloquent\SoftDeletingTrait;
class PrintSize extends Eloquent {
use SoftDeletingTrait;
protected $dates = ['deleted_at'];
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'print_sizes';
protected $fillable = array( 'title', 'description', 'cost_actual', 'cost_client', 'status', 'created_at', 'updated_at', 'deleted_at' );
}