Laravel maatwebsite import and fill a column with a select form - laravel

I'm using maatwebsite's Excel import library to import employees into a database table and it works quite well. However, on the View page where I select the Excel file to import, I have a select drop-down that shows data from the related Companies table, so that that specific selected Company is posted to all the currently imported employees' Comp_id foreign key. I have created the hasMany and belongsTo relations in the respective Company and Employee models.
The data sent in the EmployeeController:
public function viewImport()
{
$employees = Employee::all();
return view('viewImport',
['companies' => Company::pluck('CompanyName', 'Comp_id')
])->withEmployees($employees);
}
public function importExcel(Request $request)
{
if($request->hasFile('import_file')){
$path = $request->file('import_file')->getRealPath();
$data = Excel::load($path, function($reader) {})->get();
$company = Company::.....; /*???????????????
if(!empty($data) && $data->count()){
foreach ($data->toArray() as $key => $value) {
if(!empty($value)){
foreach ($value as $v) {
$insert[] = ['name'=> $v['name'],
'surname'=> $v['surname'],
'idno'=> $v['idno'],
'phone'=> $v['phone'],
'salary'=> $v['salary'],
'dob'=> $v['dob'],
'jobdescription'=> $v['jobdescription'],
'initials'=> $v['initials'],
'Comp_id' => .... /* ???????????????
];
I've included the Company model as class in the EmployeeController.
I want to add a field insertion 'Comp_id' => .... with the Comp_id value of the selected drop-down. How do I create the $company variable in the function so that the selected Comp_id can be inserted for every row? Or is there a completely different way?
Thanks in advance.

Nailed it with 'comp_id' => $request->get('Comp_id').
foreach ($data->toArray() as $key => $value) {
if(!empty($value)){
foreach ($value as $v) {
$insert[] = ['name'=> $v['name'],
'surname'=> $v['surname'],
'idno'=> $v['idno'],
'phone'=> $v['phone'],
'salary'=> $v['salary'],
'dob'=> $v['dob'],
'jobdescription'=> $v['jobdescription'],
'initials'=> $v['initials'],
'comp_id' => $request->get('Comp_id'),
];

assuming your view has a form with a select with your Comp_id, you should be able to grab it from your incomming request:
$company->comp_id = $request->get('Comp_id');
just a hint: have a look at laravel's mass assignment feature.

Related

error on multiple data updates that belong to two entities in laravel

error on multiple data updates that belong to two entities all data is updated but child table in emp_id is only first insert in all columns. database image attached.
public function update(Request $request, $id)
{
$announcement = Announcement::find($id);
$dates = explode(' to ' ,$request->date);
$announcement->title = $request->title;
$announcement->date = $dates[0];
$announcement->todate = $dates[1] ?? null;
$announcement->departments = implode(',',$request->department);
$announcement->descriptions = $request->descriptions;
$announcement->update();
if($request->employees){
foreach ($request->employees as $index => $emp_id) {
$announcement->announceduser()->where('announcement_id',$announcement->id)->update([
'emp_id' => $request->employees[$index]
]);
}
}
return redirect()->route('announcement.index')->with('success', 'Announcement Updated!!');
}
enter image description here
it is only update first emp_id in all table

Laravel 9 hasMany relationship not working

I have a model with a relationship with another model, when calling the relationship in the controller it gives me
Exception: Property [products] does not exist on the Eloquent builder instance.
model:
public function products(): HasMany
{
return $this->hasMany(CartProduct::class,'cart_id','id');
}
controller
public function showCartOfAuth()
{
$id =auth()->guard('customers')->user()->id;
$cart = Cart::where('customer_id',$id)->get();
$products = Cart::where('customer_id',$id)->products->get();
$response = [
'cart' => $cart,
'items' => $products
];
return response($response,200);
}
Can you try this, please: Cart::with('products')->where('customer_id',$id)->get();
The way you have implemented requires atleast two database queries.
One: $cart = Cart::where('customer_id',$id)->get();
Two: Cart::where('customer_id',$id)->first()->products; //maybe a third query to fetch the products
For better performance you should
public function showCartOfAuth()
{
$id =auth()->guard('customers')->user()->id;
// Either Option 1
// Possibly 2 database queries, one to fetch the Cart and another to fetch Products for the Cart
$cart = Cart::where('customer_id',$id)->first();
$products = $cart->products;
$response = [
'cart' => $cart,
'items' => $products
];
// OR Option 2
// One database query using eager loading
$cart = Cart::with('products')->where('customer_id', $id)->first();
$response = ['cart' => $cart];
return response($response,200);
}
If you use option 2 from above then instead of $items you can use $cart->products

Laravel, how to insert multiple rows in database using foreach in controller?

Can I ask the question to how to insert the multiple data or information in database using foreach at the controller?
$data = [];
$period = CarbonPeriod::create('2020-09-10', '2020-09-20')->toArray();
foreach ($period as $key => $value) {
$row['register_date'] = $value->format('Y-m-d');
array_push($data, $row);
}
User::insert($data);

I want to bring all the columns from laravel at once

The "users" table contains the name, age, and addr columns. If I want to print these three columns, I need to do something like this:
$users = DB::table('users')->get();
foreach ($users as $user) {
echo $user->name.",";
echo $user->age.",";
echo $user->addr."<br>";
}
I want to output all the columns, even if not each. So I tried this.
$users = DB::table('users')->get();
foreach ($users as $user) {
print_r($user);
}
result.
App\Model\Users Object
(
[timestamps] =>
[connection:protected] => mysql
[table:protected] => main_settings
[primaryKey:protected] => id
[keyType:protected] => int
[incrementing] => 1
[with:protected] => Array
(
......
I did not get the result I wanted. How can I display all the columns at once?
After registering the question, I found the answer.
$users = DB::table('users')->get()->toArray();
foreach ($users as $user) {
print_r($user);
}
Using toArray () gives me the result I want.
I suggest you to make use of model in laravel to add/edit/delete/fetch data.
you can try the below code for fetching the user table data.
$users = App\User::all();
foreach($users as $user) {
dd($user);
}
Note : use User model in your class before accessing it.
If you want to fetch data using SQL Raw query then try the below code.
$users = DB::table('users')->get();
foreach ($users as $key=>$user) {
dd($key,$user);
}

How can i decode json data if i saved in array laravel?

I have 2 two tables: one is an admission and the other is a class table. I am saving class id in admission class field of admission table by json_encode method.
My controller
public function store(Request $request)
{
$inputs = $request->all();
$admission = new Admission;
$admission->school_id = Auth::User()->id;
$admission->admission_classes=json_encode($inputs['admission_classes']);
$admission->save();
}
My index function
public function index(Request $request) {
$school_id= Auth::user()->id;
$admissions= Admission::where('school_id',$school_id)->orderBy('id','desc')->paginate(10);
return view('frontend.index',compact('admissions','active_class'));
}
My view
#foreach($admissions as $i => $admission)
{{ $admission->admission_classes }}
#endforeach
I am getting data in this way:-
["1","2","4","5","6","7","8","9"]
But I want to get in this format:
Nursery,Class 1, Class2, Class3 etc
My class controller
class Classes extends Authenticatable
{
use EntrustUserTrait;
use Billable;
use Messagable;
protected $fillable = [
'name','status'
];
}
You need to save integer value in as json array and do the following code
$integerIDs = array_map('intval', $inputs['admission_classes']);
$admission->admission_classes= json_encode($integerIDs);
public function index(Request $request){
$admissions = DB::select('SELECT a.*, GROUP_CONCAT(c.name) as classes FROM academy as a LEFT JOIN class c ON JSON_CONTAINS(a.classes, CAST(c.id as JSON), '$') WHERE a.school_id =2 GROUP BY a.id');
$admissions = $this->arrayPaginator($admissions, $request);
return view('frontend.index',compact('admissions','active_class'));
}
public function arrayPaginator($array, $request)
{
$page = Input::get('page', 1);
$perPage = 10;
$offset = ($page * $perPage) - $perPage;
return new LengthAwarePaginator(array_slice($array, $offset,
$perPage, true), count($array), $perPage, $page,
['path' => $request->url(), 'query' => $request->query()]);
}
I have not checked the code hope this will help u to continue.......
The best way to achieve this would be to have a one-to-many relationship with App\Classes.
However, since you already have something up and running, I would probably do it like this.
First, I would cast admission_classes to an array. This makes sure that admission_classes will always be casted to an array whenever it is fetched. It makes it easier for us to work with it.
protected $casts = [
'admission_classes' => 'array'
];
Finally, while fetching your admission records, you would also need to map over it and hydrate the Classes from its ids. This is how I'd try to achieve it.
$admissions = Admission::where('school_id',$school_id)
->orderBy('id','desc')
->paginate(10)
->map(function($admission) {
return array_map(function($class) {
$class = Classes::find($class);
return isset($class) ? $class->name : '';
}, $admission->admission_classes);
});
You will notice that I wrapped the Classes::find() method into the optional() helper. This is because, in case, a record is not found, it will not fail.
Finally, to print your class names in your blade, you would do something like this:
implode(',', $admission->admission_classes);

Resources