laravel call to undefined method app\models\User:id() - laravel

I have been trying to create a point system, so after much effort i am getting this error which i could not figure out how to solve it because this is my first time working so deep
I have checked code but couldn't pinpoint the error
call to undefined app\models\User:id()
point model
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\MorphTo;
class Point extends Model
{
use HasFactory;
const TABLE = 'points';
protected $table = self::TABLE;
protected $fillable = [
'id', 'amount', 'message', 'current_points'
];
public function pointable(): MorphTo
{
return $this->morphTo();
}
public function getCurrentPoints(Model $pointable)
{
$currentPoints = Point::where('pointable_id', $pointable->id())
->where('pointable_type', $pointable->getMorphClass())
->orderBy('created_at', 'desc')
->pluck('current_points')->first();
if($currentPoints){
$currentPoints = 0;
}
return $currentPoints;
}
public function addAwards(Model $pointable, $amount, $message)
{
$award = new Static();
$award->amount = $amount;
$award->current_points = $this->getCurrentPoints($pointable) + $amount;
$award->message = $message
$pointable->awards()->save($award);
return $award;
}
}
pointable model
<?php
namespace App\Models;
interface pointable
{
public function awards();
public function countAwards();
public function addPoints($amount, $message);
}
hasPoints Traits
<?php
namespace App\Traits;
use App\Models\Point;
trait HasPoints
{
public function awards($amount = null)
{
return $this->morphMany(Point::class, 'pointable')
->orderBy('created_at', 'desc')
->take($amount);
}
public function countAwards()
{
return $this->awards()->count();
}
public function currentPoints()
{
return (new Point())->getCurrentPoints($this);
}
public function addPoints($amount, $message)
{
return (new Point())->addAwards($this, $amount, $message);
}
}
AwardPointLItener
?php
namespace App\Listeners;
use App\Events\ReplyWasCreated;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
class AwardPointForNewReply
{
public function handle(ReplyWasCreated $event)
{
$amount = config('points.rewards.new_reply');
$message = 'User Created A New Reply';
$author = $event->reply->user;
$author->addPoints($amount, $message);
}
}
ReplyEvent
<?php
namespace App\Events;
use App\Models\Reply as Replyers;
use Illuminate\Queue\SerializesModels;
class ReplyWasCreated
{
use SerializesModels;
public $reply;
public function __construct(Replyers $reply)
{
$this->reply = $reply;
}
}
livewire reply componet
use Livewire\Component;
use App\Models\Reply as Replys;
class Reply extends Component
{
public $thread;
public $username;
public $reply_text;
public $replyCommentId = NULL;
protected $rules = [
'reply_text' => 'required'
];
public function mount(Thread $thread)
{
$this->thread = $thread;
}
public function render()
{
$replys = Replys::whereNull('parent_id')
->with('replies')
->with('user')
->where('thread_id', $this->thread->id)->paginate()->withQueryString();
return view('livewire.thread.reply',[
'replys' => $replys,
]);
}
public function save_reply()
{
$this->validate();
$replyevent = Replys::create([
'thread_id' => $this->thread->id,
'user_id' => auth()->user()->id,
'reply_text' => $this->reply_text,
'parent_id' => $this->replyCommentId
]);
event(new ReplyWasCreated($replyevent));
// $this->username = '';
$this->reply_text = '';
$this->replyCommentId = NULL;
}
public function deleteReply($id)
{
$reply = Replys::FindOrFail($id);
$reply->delete();
}
public function replys($replyId)
{
$this->replyCommentId = $replyId;
}
}

To get the id of a model, you simply access its id property. There is no id() method.
$currentPoints = Point::where('pointable_id', $pointable->id)

Related

How do I import specific columns from XLSX to an array (Laravel)?

I need to import a table into an array. And import not all cells, but only 2 columns.
For example, from
A
B
C
D
F
1
2
3
4
5
6
7
8
9
10
to
[
{
'A' => 1,
'F' => 5,
},
{
'A' => 6,
'F' => 10,
}
]
app\Imports\PricesImport.php
<?php
namespace App\Imports;
use Maatwebsite\Excel\Concerns\ToArray;
use Maatwebsite\Excel\Concerns\Importable;
class PricesImport implements ToArray
{
use Importable;
public function array(array $rows)
{
return array($rows[0], $rows[4]);
}
}
And the call in the controller:
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Imports\PricesImport;
use Maatwebsite\Excel\Facades\Excel;
class SomeController extends Controller
{
public function import(Request $request) {
$array = Excel::toArray(new PricesImport, $request->file('file'));
}
}
But it doesn't work. What am I doing wrong?
Update
Tried this option, but it returns all columns, not 2 specific columns
app\Imports\PricesImport.php
<?php
namespace App\Imports;
use Maatwebsite\Excel\Concerns\ToArray;
use Maatwebsite\Excel\Concerns\Importable;
class PricesImport implements ToArray
{
use Importable;
private $data;
public function __construct()
{
$this->data = [];
}
public function array(array $rows)
{
foreach ($rows as $row) {
$row = $row->toArray();
$this->data[] = array('sku' => $row[0], 'price' => $row[4]);
}
return $this->data;
}
}
Thanks to a hint from Patrick Brouwers, this worked:
app\Imports\PricesImport.php
<?php
namespace App\Imports;
use Maatwebsite\Excel\Concerns\ToArray;
class PricesImport implements ToArray
{
private $data;
public function __construct()
{
$this->data = [];
}
public function array(array $rows)
{
foreach ($rows as $row) {
$this->data[] = array('sku' => $row[0], 'price' => $row[4]);
}
}
public function getArray(): array
{
return $this->data;
}
}
And the call in the controller:
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Imports\PricesImport;
use Maatwebsite\Excel\Facades\Excel;
class SomeController extends Controller
{
public function import(Request $request) {
$import = new PricesImport;
Excel::import($import, $request->file('file'));
$array = $import->getArray();
}
}

Argument 1 passed to ::showAll() must be an instance of Collection, instance ofCollection given, called BuyerProductController.php on line 23

I don't understand this mistake, can someone help me?
I am taking a course on ApiRestfull and the code works for the teacher but I can't get it to work for me
I am using laravel 5.8*
The error he shows me is this: Error:
Argument 1 passed to App\Http\Controllers\ApiController::showAll() must be an instance of Illuminate\Database\Eloquent\Collection, instance of Illuminate\Support\Collection given, called in C:\laragon\www\udemy-apirestfull\app\Http\Controllers\Buyer\BuyerProductController.php on line 23
BuyerProductController.php:
<?php
namespace App\Http\Controllers\Buyer;
use App\Buyer;
use Illuminate\Http\Request;
use App\Http\Controllers\ApiController;
class BuyerProductController extends ApiController
{
/**
* Display a listing of the resource.
*
* #return \Illuminate\Http\Response
*/
public function index(Buyer $buyer)
{
$products = $buyer->transactions()->with('product')
->get()
->pluck('product');
return $this->showAll($products);
}
}
ApiController:
<?php
namespace App\Http\Controllers;
use App\Traits\ApiResponser;
use Illuminate\Http\Request;
class ApiController extends Controller
{
use ApiResponser;
}
ApiResponser:
<?php
namespace App\Traits;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Collection;
trait ApiResponser
{
private function successResponse($data, $code)
{
return response()->json($data, $code);
}
protected function errorResponse($message, $code)
{
return response()->json(['error' => $message, 'code' => $code], $code);
}
protected function showAll(Collection $collection, $code = 200)
{
return $this->successResponse(['data' => $collection], $code);
}
protected function showOne(Model $instance, $code = 200)
{
return $this->successResponse(['data' => $instance], $code);
}
}
Buyer model:
<?php
namespace App;
use App\Transaction;
use App\Scopes\BuyerScope;
class Buyer extends User
{
protected static function boot()
{
parent::boot();
static::addGlobalScope(new BuyerScope);
}
public function transactions()
{
return $this->hasMany(Transaction::class);
}
}
Product Model:
<?php
namespace App;
use App\Seller;
use App\Category;
use App\Transaction;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
class Product extends Model
{
use SoftDeletes;
const PRODUCTO_DISPONIBLE = 'disponible';
const PRODUCTO_NO_DISPONIBLE = 'no disponible';
protected $dates = ['deleted_at'];
protected $fillable = [
'name',
'description',
'quantity',
'status',
'image',
'seller_id',
];
public function estaDisponible()
{
return $this->status == Product::PRODUCTO_DISPONIBLE;
}
public function seller()
{
return $this->belongsTo(Seller::class);
}
public function transactions()
{
return $this->hasMany(Transaction::class);
}
public function categories()
{
return $this->belongsToMany(Category::class);
}
}
Transaction Model:
<?php
namespace App;
use App\Buyer;
use App\Product;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\SoftDeletes;
class Transaction extends Model
{
use SoftDeletes;
protected $dates = ['deleted_at'];
protected $fillable = [
'quantity',
'buyer_id',
'product_id',
];
public function buyer()
{
return $this->belongsTo(Buyer::class);
}
public function product()
{
return $this->belongsTo(Product::class);
}
}
Illuminate\Database\Eloquent\Collection extends Illuminate\Support\Collection
So if not mandatory, you can change the signature of showAll method to accept Illuminate\Support\Collection as a parameter
There will be no error if the parameter supplied will be an instance of Illuminate\Database\Eloquent\Collection
<?php
namespace App\Traits;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Collection; //Changed here
trait ApiResponser
{
private function successResponse($data, $code)
{
return response()->json($data, $code);
}
protected function errorResponse($message, $code)
{
return response()->json(['error' => $message, 'code' => $code], $code);
}
protected function showAll(Collection $collection, $code = 200)
{
return $this->successResponse(['data' => $collection], $code);
}
protected function showOne(Model $instance, $code = 200)
{
return $this->successResponse(['data' => $instance], $code);
}
}

How do I see published posts count with Eloquent using a ServiceProvider

I have a Blog Categories in the sidebar.blade.php
#foreach ($categories as $category)
<li>
<i class="fa fa-angle- right"></i> {{$category->title}}
<span class="badge pull-right">{{$category->posts()->count()}}</span>
</li>
#endforeach
But this count give me all the posts in my database, even the ones that are scheduled to post at a later date.
PostsController
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Post;
use App\Category;
class PostsController extends Controller
{
protected $limit = 3;
public function index()
{
$posts = Post::with('author')
->latestFirst()
->published()
->paginate($this->limit);
return view('posts.index', compact('posts'));
}
public function category(Category $category)
{
$categoryName = $category->title;
$posts = $category->posts()
->with('author')
->latestFirst()
->published()
->paginate($this->limit);
return view('posts.index', compact('posts', 'categoryName'));
}
Here's the Post.php
namespace App;
use Illuminate\Database\Eloquent\Model;
use Carbon\Carbon;
use GrahamCampbell\Markdown\Facades\Markdown;
class Post extends Model
{
//Table Name
protected $table = 'posts';
// Primary Key
public $primaryKey = 'id';
// Timestamps
public $timestamps = true;
/*protected $fillable = [
'title',
'excerpt',
'body',
'categery_id',
'image',
];*/
protected $dates = ['published_at'];
public function author()
{
return $this->belongsTo(User::class);
}
public function category()
{
return $this->belongsTo(Category::class);
}
public function getImageUrlAttribute($value)
{
$imageUrl = "";
if( ! is_null($this->image))
{
$imagePath = public_path() . "/img/" . $this->image;
if(file_exists($imagePath)) $imageUrl = asset("img/" . $this->image);
}
return $imageUrl;
}
public function getDateAttribute()
{
return is_null($this->published_at) ? '' : $this->published_at->diffForHumans();
}
public function getExcerptHtmlAttribute(){
return $this->excerpt ? Markdown::convertToHtml(e($this->excerpt)) : NULL;
}
public function getBodyHtmlAttribute()
{
return $this->body ? Markdown::convertToHtml(e($this->body)) : NULL;
}
public function scopeLatestFirst($query)
{
return $query->orderBy('published_at', 'desc');
}
public function scopePublished($query)
{
return $query->where('published_at', '<=', Carbon::now());
}
}
Here's my Category.php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Category extends Model
{
protected $table = 'categories';
/*protected $fillable = [
'title',
'excerpt',
'body',
'categery_id',
'image',
'slug'
];*/
public function posts()
{
return $this->hasMany(Post::class);
}
public function getRouteKeyName()
{
return 'slug';
}
}
Web.php
Route::get('/', 'PagesController#index');
Route::get('/about', 'PagesController#about');
Route::get('/category/{category}', [
'uses' => 'PostsController#category',
'as' => 'category'
]);
Route::resource('books', 'BooksController');
Route::resource('posts', 'PostsController');
Route::resource('categories', 'CategoriesController', ['except'=> ['create']]);
ComposerServiceProvider.php
namespace App\Providers;
use Illuminate\Support\ServiceProvider;
use App\Category;
use App\Post;
class ComposerServiceProvider extends ServiceProvider
{
public function boot()
{
view()->composer('layouts.sidebar', function($view){
$categories = Category::with(['posts' => function($query){
$query->published();
}])->orderBy('title', 'asc')->get();
return $view->with('categories', $categories);
});
}
}
To recap on what I need done...
I want to just have my published post to be accounted for in the counter to show, not all the of the posts in my database..
(<span class="badge pull-right">{{$category->posts->count()}}</span>)
Post.php
public function scopePublished($query)
{
return $query->where('published_at', '<=', Carbon::now());
}
But this is not working right for me, does anyone know why?
Try this one:
<span class="badge pull-right">{{$category->posts()->published()->count()}}</span>
Didn't try but this should do the trick.

Couldn't get relation model value in maatwebsite laravel

The work of this function is to generate report of specific condition. Thus i am generating report with two tables ( User and Booking ) With primary key is userid and bookingid. Both the table is be clubbed into relations. Now i want to generate excel with using maatwebsite package at this condition. From (booking table) and to (booking table) with ticketstatus (booking table) and also with usertype ( from usertable ). For example From 01.09.2018 to 23.09.2018 with ticket status as "booked " and usertype as "Normal or agent". But i am getting an error, i am using FromQuery method in maatwebsite to perform this function.
I am adding all the codes here, User Model :
<?php
namespace App;
use App\Booking;
use App\Wallet;
use Illuminate\Database\Eloquent\Model;
class User extends Model
{
protected $primaryKey = 'userid';
protected $fillable = ['name', 'phone', 'email','password','usertype'];
protected $dates = [
'createdAt'
];
const CREATED_AT = 'createdAt';
const UPDATED_AT = 'updatedAt';
public function bookings()
{
return $this->hasMany('App\Booking', 'userid');
}
public function walletUsers()
{
return $this->hasOne('App\Wallet', 'userid');
}
public function supports()
{
return $this->hasMany('App\Help', 'userid');
}
public function getNameAttribute($value)
{
return ucfirst($value);
}
}
Booking Model :
<?php
namespace App;
use Carbon\Carbon;
use Illuminate\Database\Eloquent\Model;
class Booking extends Model
{
protected $primaryKey = 'bookingid';
protected $dates = [
'createdAt','updatedAt'
];
const CREATED_AT = 'createdAt';
const UPDATED_AT = 'updatedAt';
public function users()
{
return $this->belongsTo('App\User', 'userid');
}
public function getDateOfIssueAttribute($value) {
return Carbon::parse($value)->format('d-M-Y , h:m a');
}
public function getDateOfCancellationAttribute($value) {
return Carbon::parse($value)->format('d-M-Y , h:m a');
}
public function getDojAttribute($value) {
return Carbon::parse($value)->format('d-M-Y , h:m a');
}
}
Now Controller :
public function report(Request $request){
$from = $request->from;
$to = $request->to;
$bookingtype = $request->bookingtype;
$usertype = $request->usertype;
return (new BookingsExport($from, $to, $bookingtype, $usertype))->download('invoices.xlsx');
}
Route :
Route::post('/admin/reports/collect',[
'uses' => 'ReportController#report',
'as' => 'reports.generate'
]);
Maatwebsite Class:
<?php
namespace App\Exports;
use App\Booking;
use App\User;
use Carbon\Carbon;
use App\Http\Controllers\ReportController;
use Maatwebsite\Excel\Concerns\FromQuery;
use Maatwebsite\Excel\Concerns\Exportable;
use Maatwebsite\Excel\Concerns\WithHeadings;
use Maatwebsite\Excel\Concerns\WithStrictNullComparison;
use Maatwebsite\Excel\Concerns\ShouldAutoSize;
use PhpOffice\PhpSpreadsheet\Shared\Date;
use Maatwebsite\Excel\Concerns\WithColumnFormatting;
use PhpOffice\PhpSpreadsheet\Style\NumberFormat;
use Maatwebsite\Excel\Concerns\WithMapping;
class BookingsExport implements FromQuery, WithStrictNullComparison, WithHeadings, ShouldAutoSize, WithColumnFormatting, WithMapping {
use Exportable;
public function __construct($from, $to, $bookingtype, $usertype)
{
$this->from = $from;
$this->to = $to;
$this->bookingtype = $bookingtype;
$this->usertype = $usertype;
}
public function headings(): array
{
return [
'Booking Id',
'Block Key',
'Bus Type',
'DOJ',
'status',
'Created At',
'Updated At',
'Usertype',
'Name'
];
}
public function map($booking): array
{
return [
$booking->bookingid,
$booking->blockkey,
$booking->busType,
$booking->doj,
$booking->status,
$booking->createdAt,
$booking->updatedAt,
$booking->users->usertype,
$booking->users->name
];
}
public function columnFormats(): array
{
return [
'D' => 'dd-mm-yyy',
'E' => NumberFormat::FORMAT_DATE_DDMMYYYY
];
}
public function query()
{
$from = $this->from;
$to = $this->to;
$bookingtype = $this->bookingtype;
$usertype = $this->usertype;
if(isset($from) && isset($to) && is_null($bookingtype) && is_null($usertype))
{
return Booking::query()->whereBetween('createdAt',[$from, $to]);
}
if(isset($from) && isset($to) && isset($bookingtype) && is_null($usertype))
{
return Booking::query()->whereBetween('createdAt',[$from, $to])->where('status','=', $bookingtype);
}
if(isset($from) && isset($to) && isset($bookingtype) && isset($usertype))
{
return Booking::query()->with('users')->whereHas("users", function($subQuery){
$subQuery->where("usertype", "=", $usertype);})->whereBetween('createdAt',[$from, $to])->where('status','=', $bookingtype);
}
}
}
The error i am getting is "Undefined variable: usertype" from the last query of Maatwebsite class file. But i am seeding all the values from controller to this, i even dd($usertype) but i am getting the value as agent, but it shows error while using in it query ! Kindly guide

InvalidArgumentException route notdefined

I have error like (1/1) InvalidArgumentException
Route [home] not defined. whenever i used the store function but i'm pretty sure that i use the redirect method right what could be the possible error, all i wanted was to redirect to home once the store method is done.
web.php
<?php
Route::get('/', function () {
return view('main');
});
Route::get('/create', 'BuildingController#createBuilding');
Route::post('/store', 'BuildingController#store');
Route::post('home', 'BuildingController#getAllBuilding');
Building.php
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Building extends Model
{
public $timestamps = false;
protected $fillable = [
'id',
'building_name',
'building_information',
'building_image'
];
}
BuildingController.php
<?php
namespace App\Http\Controllers;
use App\Building;
use Image;
use Illuminate\Http\Request;
use App\Repositories\Building\BuildingRepository;
class BuildingController extends Controller
{
/**
* Display a listing of the resource.
*
* #return \Illuminate\Http\Response
*/
private $building;
public function __construct(BuildingRepository $building)
{
$this->building = $building;
}
public function createBuilding()
{
return view('building.create');
}
public function store(Request $request)
{
$this->validate($request, array(
'building_name'=>'required',
'building_information'=>'required',
'building_image' => 'required'
));
$image = $request->file('building_image');
$filename = time() . '.' . $image->getClientOriginalExtension();
$location = public_path('images/' .$filename);
Image::make($image)->resize(800,400)->save($location);
$buildings = array('building_name' => $request->building_name,
'building_information' => $request->building_information,
'building_image' => $filename);
$this->building->create($buildings);
return redirect()->route('home');
}
public function getAllBuilding()
{
$buildings = $this->building->getAll();
return view('building.home')->with('buildings', $buildings);
}
public function getSpecificRecord()
{
$buildings = $this->building->getById(1);
return view('building.show')->with('buildings', $buildings);
}
}
EloquentBuilding.php
<?php
namespace App\Repositories\Building;
use \App\Building;
class EloquentBuilding implements BuildingRepository
{
private $model;
public function __construct(Building $model)
{
$this->model = $model;
}
public function getById($id)
{
return $this->model->findOrFail($id);
}
public function getAll()
{
return $this->model->all();
}
public function create(array $attributes)
{
return $this->model->create($attributes);
}
public function update($id, array $attributes)
{
}
public function delete($id)
{
}
}
BuildingRepository.php
<?php
namespace App\Repositories\Building;
interface BuildingRepository
{
public function getById($id);
public function getAll();
public function create(array $attributes);
public function update($id, array $attributes);
public function delete($id);
}
Since you're using route(), you need to name the route. Also, make it get:
Route::get('home', 'BuildingController#getAllBuilding')->name('home');
Or:
Route::get('home', ['as' => 'home', 'uses' => 'BuildingController#getAllBuilding']);
You are trying to use route with post, replace it with get and also add/specify name attribute to call route using name.
Route::get('home', 'BuildingController#getAllBuilding')->name('home');
OR
Route::get('home', ['as' => 'home', 'uses' => 'BuildingController#getAllBuilding']);
Above both are comes with same output...

Resources