i want to import from excel using php excel from my codeigniter with current cell containt current text
cell1
cell2
A
1
B
2
C
3
i want just cell except B in cell1 to insert database
my controller
public function import_excel(){
if (isset($_FILES["fileExcel"]["name"])) {
$path = $_FILES["fileExcel"]["tmp_name"];
$object = IOFactory::load($path);
foreach($object->getWorksheetIterator() as $worksheet)
{
$highestRow = $worksheet->getHighestRow();
$highestColumn = $worksheet->getHighestColumn();
for($row=2; $row<=$highestRow; $row++)
{
$cell1= $worksheet->getCellByColumnAndRow(0, $row)->getValue();
$cell2= $worksheet->getCellByColumnAndRow(1, $row)->getValue();
$temp_data[] = array(
'cell1' => $cell1,
'cell2' => $cell2,
);
}
}
if($cell1 == 'B'){
}else{
$this->load->model('M_Admin');
$insert = $this->M_Admin->insert($temp_data);
}
but this failed and data still insert. please help me and many thanks you for help.
I never use phpexcel before, but if it's array and consider that $cell1 is a string/text, I guess you can try to use this:
for($row=2; $row<=$highestRow; $row++)
{
$cell1= $worksheet->getCellByColumnAndRow(0, $row)->getValue();
$cell2= $worksheet->getCellByColumnAndRow(1, $row)->getValue();
//cell value you want to hide
if ($cell1 == 'B') {
$cell1 = 'xxx'; //overwrite that value into something
}
$temp_data[] = array(
'cell1' => $cell1,
'cell2' => $cell2,
);
}
note: I'm using codeigniter 3
Related
I loop trough an eloquent Collection and I want to add the data to another Collection called "$tagCollection". If an entry with the same tag_id already exists I only want to increase the rating-column for the existing entry.
At the moment it looks like this. Has anyone an Idea?
$tagCollection = collect();
$entries->each(function($entry) use($tagCollection){
$tagId = $entry->tag_id;
//something like this
if($tagCollection->contains('tag_id', $tagId)){
$tagCollection->update ('rating' => $oldRating + 0.5)
} else{
$tagCollection->push(array(
'tag_id' => $tagId,
'rating' => 0.35
));
}
});
I also tried to use ->pull() to remove the Item out of the Collection and then push it again with the new rating but I also do not know how
Can you do it with array instead of collection? For example:
$tagArray = [];
$entries->each(function ($entry) use (&$tagArray) {
if (isset($tagArray[$entry['tag_id']])) {
$tagArray[$entry['tag_id']] += 0.5;
} else {
$tagArray[$entry['tag_id']] = 0.35;
}
});
If the end goal is to update all the entries present in $entries that belong to a specific $tagId, then you can do this
$entryIds = $entries->where('tag_id',$tagId)->pluck('id')->toArray();
Entry::whereIn('id', $entryIds)->update(['rating' => \DB::raw('rating + 0.5')]);
And thats it.
I'm working with Lumen framework v5.8 (it's the same as Laravel)
I have a command for read a big XML (400Mo) and update datas in database from datas in this file, this is my code :
public function handle()
{
$reader = new XMLReader();
$reader->open(storage_path('app/mesh2019.xml'));
while ($reader->read()) {
switch ($reader->nodeType) {
case (XMLREADER::ELEMENT):
if ($reader->localName === 'DescriptorRecord') {
$node = new SimpleXMLElement($reader->readOuterXML());
$meshId = $node->DescriptorUI;
$name = (string) $node->DescriptorName->String;
$conditionId = Condition::where('mesh_id', $meshId)->first();
if ($conditionId) {
ConditionTranslation::where(['condition_id' => $conditionId->id, 'locale' => 'fr'])->update(['name' => $name]);
$this->info(memory_get_usage());
}
}
}
}
}
So, I have to find in the XML each DescriptorUI element, the value corresponds to the mesh_id attribute of my class Condition.
So, with $conditionId = Condition::where('mesh_id', $meshId)->first(); I get the Condition object.
After that, I need to update a child of Condition => ConditionTranslation. So I just get the element DescriptorName and update the name field of ConditionTranslation
At the end of the script, you can see $this->info(memory_get_usage());, and when I run the command the value increases each time until the script runs very very slowly...and never ends.
How can I optimize this script ?
Thanks !
Edit : Is there a way with Laravel for preupdate multiple object, and save just one time at the end all objects ? Like the flush() method of Symfony
There is a solution with ON DUPLICATE KEY UPDATE
public function handle()
{
$reader = new XMLReader();
$reader->open(storage_path('app/mesh2019.xml'));
$keyValues = [];
while ($reader->read()) {
switch ($reader->nodeType) {
case (XMLREADER::ELEMENT):
if ($reader->localName === 'DescriptorRecord') {
$node = new SimpleXMLElement($reader->readOuterXML());
$meshId = $node->DescriptorUI;
$name = (string) $node->DescriptorName->String;
$conditionId = Condition::where('mesh_id', $meshId)->value('id');
if ($conditionId) {
$keyValues[] = "($conditionId, '".str_replace("'","\'",$name)."')";
}
}
}
}
if (count($keyValues)) {
\DB::query('INSERT into `conditions` (id, name) VALUES '.implode(', ', $keyValues).' ON DUPLICATE KEY UPDATE name = VALUES(name)');
}
}
I'm trying to save a data to my database coming from 2 inputs which has multiple values. The scenario is that after a product has been saved, data will be save to my another table with columns 'product_id','price','size'. How ever when I tried to run my code, only the first value is saved in the column 'size', the data in 'price' are fine.
<input name="fix_size[]">
<input name="fix_price[]">
foreach($request->fix_price as $prc){
$cprice = new ContainerPrice;
$cprice->product_id = $id;
$cprice->price = $prc;
foreach($request->fix_size as $size){
$cprice->size = $size;
}
$cprice->save();
}
Remember, fix_size and fix_price are arrays.
You have to get the respective pairs of each fix_size and fix_price. So you have to monitor the index in the loop.
This is one of the possible solution in your problem:
$fix_sizes = $request->fix_size;
foreach($request->fix_price as $i => $prc){
$cprice = new ContainerPrice;
$cprice->product_id = $id;
$cprice->price = $prc;
$cprice->size = $fix_sizes[$i];
$cprice->save();
}
I may suggest to you to master the basic principles of programming and learn to debug codes by yourself.
Try this
foreach($request->fix_price as $prc){
foreach($request->fixed_size as $size){
$cprice = new ContainerPrice;
$cprice->product_id = $id;
$cprice->price = $prc;
$cprice->size = $size;
$cprice->save();
}
}
You could try this:
foreach($request->fix_price as $key => $prc) {
$cprice = new ContainerPrice;
$cprice->product_id = $id;
$cprice->price = $prc;
$cprice->size = $request->input('size')[$key];
$cprice->save();
}
The problem you had is because you loop over all elements inside the main loop and keeping only the last element. In other words, in the foreach loop, you are constantly overriding the $cprice->size property with the last you find.
Now with this code you access the "size" which has the same index as your "price".
I am using laravel backpack and recently enabled $this->crud->enableAjaxTable(); in my crud because there was a lot of data to show.
But now I am not able to color my crud entries depending upon a expiry_date as I was doing before by overriding list.blade.php like this:
#if (!$crud->ajaxTable())
#foreach ($entries as $k => $entry)
<?php
use Carbon\Carbon;
$today_date = Carbon::now();
$data_difference = $today_date->diffInDays(Carbon::parse($entry->expiry_date), false);
if($data_difference <= 7 && $data_difference >= 0) {
$color="#FF9900";
} elseif($data_difference < 0) {
$color="#EA2C12";
} elseif($data_difference > 7) {
$color="#539E05";
}
?>
<tr data-entry-id="{{ $entry->getKey() }}" style="color: {{$color}}">
Maybe because of this:
#if (!$crud->ajaxTable())
I tried to customize the AjaxTable.php search query using this link but I was not successful. Here is the code I tried in my ExampleCrudController by overriding search query of ajax:
public function search()
{
$this->crud->hasAccessOrFail('list');
// create an array with the names of the searchable columns
$columns = collect($this->crud->columns)
->reject(function ($column, $key) {
// the select_multiple, model_function and model_function_attribute columns are not searchable
return isset($column['type']) && ($column['type'] == 'select_multiple' || $column['type'] == 'model_function' || $column['type'] == 'model_function_attribute');
})
->pluck('name')
// add the primary key, otherwise the buttons won't work
->merge($this->crud->model->getKeyName())
->toArray();
// structure the response in a DataTable-friendly way
$dataTable = new \LiveControl\EloquentDataTable\DataTable($this->crud->query, $columns);
// make the datatable use the column types instead of just echoing the text
$dataTable->setFormatRowFunction(function ($entry) {
$today_date = Carbon::now();
$data_difference = $today_date->diffInDays(Carbon::parse($entry->expiry_date), false);
if($data_difference <= 7 && $data_difference >= 0) {
$color="#FF9900";
} elseif($data_difference < 0) {
$color="#EA2C12";
} elseif($data_difference > 7) {
$color="#539E05";
}
// get the actual HTML for each row's cell
$row_items = $this->crud->getRowViews($entry, $this->crud, $color);
// add the buttons as the last column
if ($this->crud->buttons->where('stack', 'line')->count()) {
$row_items[] = \View::make('crud::inc.button_stack', ['stack' => 'line'])
->with('crud', $this->crud)
->with('entry', $entry)
->render();
}
// add the details_row buttons as the first column
if ($this->crud->details_row) {
array_unshift($row_items, \View::make('crud::columns.details_row_button')
->with('crud', $this->crud)
->with('entry', $entry)
->render());
}
return $row_items;
});
return $dataTable->make();
}
So my question is how can I color my crud entries depending upon expiry_date when enableajaxtable is active in laravel backpack?
When using AjaxDataTables, the rows no longer taken from the DB directly and outputed as HTML, but taken from the DB with an AJAX call. So your previous code wouldn't work, I'm afraid.
The best way I can think of to achieve the same thing would be to use a custom view for this CRUD panel, with $this->crud->setListView('your-view');. This would allow you to setup some custom JavaScript in that file, to modify DataTables.js to color the rows before it puts them in the table.
A cleaner alternative, if you're using Backpack\CRUD 3.2+, would be to customize the list.js file, to have all that logic there.
Hope it helps!
So I have my View setup like this in the controller:
public ActionResult View(Guid projectID)
{
OnboardModel model = context.onboard_projectInfos.Where(x => x.projectID == projectID).Select(x =>
new OnboardModel()
{
propertymanagername = x.propertymanagername,
propertymanagercontactemail = x.propertymanagercontactemail,
date_modified = (DateTime)x.date_modified,
projectmanagercontactnumber = x.projectmanagercontactnumber,
Developer = x.onboard_projectCreate.Developer,
status1 = x.onboard_projectCreate.status1,
ProjectName = x.onboard_projectCreate.ProjectName
}).SingleOrDefault();
var pix = projectID.ToString();
context.onboard_BuildingInfos.Where(x => x.buildprojectID == pix).GroupBy(x => x.buildprojectID).Select(g => {
model.totalres = g.Sum(b => b.numberofres);
model.totalcom = g.Sum(b => b.numberofcommer);
});
return View(model);
}
Problem is grabbing the sum of numberofres and numberofcommer from BuildingInfos.
Using .Select gives me the error:
Error CS0411 The type arguments for method 'Queryable.Select(IQueryable, Expression>)' cannot be inferred from the usage. Try specifying the type arguments explicitly.
How to I write this LINQ statement correctly?
Thanks.
You cannot modify an object within a select (you can only create a new object). Further, you can't add new properties to an existing object.
We'll assume that OnboardModel defines the totalres and totalcom properties.
var query = context.onboard_BuildingInfos
.Where(x => x.buildprojectID == pix)
.GroupBy(x => x.buildprojectID);
foreach(var g in query)
{
model.totalres = g.Sum(b => b.numberofres);
model.totalcom = g.Sum(b => b.numberofcommer);
}