I'm currently trying to create an associative array which will have two dimensions and I think a solution for this probleme could resolve problemes for array with more dimensions.
I recover data with an API which look like that :
{
"item_id": "89",
"name": "Confiture de Myrtilles",
"product_id": "737",
"meta_key": "vmm_warehouse_sg_10783",
"meta_value": "0"
},
{
"item_id": "89",
"name": "Confiture de Myrtilles",
"product_id": "737",
"meta_key": "vmm_warehouse_sg_10782",
"meta_value": "0"
},
{
"item_id": "91",
"name": "Poires Guyot (bio)",
"product_id": "690",
"meta_key": "_backorders",
"meta_value": "no"
},
{
"item_id": "91",
"name": "Poires Guyot (bio)",
"product_id": "690",
"meta_key": "_sold_individually",
"meta_value": "no"
},
I just want to create an array like this :
array[item_id->[meta_key->meta_value]]
So I have to recover the item_id which will have the role of the secondth array and after put in this array the meta_key and meta_value associated.
So for example I will have an array like this :
Products[89]["vmm_warehouse_sg_10783"->"0"
"vmm_warehouse_sg_10782"->"0"]
And an other like this :
Products[91][........]
At the end, I will have a final array like this :
Products [ [89]->{"vmm_warehouse_sg_10783"->"0","vmm_warehouse_sg_10782"->"0"}
[91]->{.....}]
I have already tried something but I'm just a beginner and I don't found solution for my problem.
$Products = $this->wpdb->get_results( $SQL_Deliveries );
//this line allow $Products to recover all data from the API
foreach ( $Products as $Product ) {
$Meta_products[] = Product->item_id;
foreach($Product as $Product_meta){
$Meta_products[$item_id]->{Product_meta->meta_key,Product_meta
->meta_value);
}
I'm sure I did mitakes in my code too, but I really don't know how to resolve this problem. Thank you for your participation !
It looks like you want a multidimensional object array.
There is a little bit of fiddling involved to declare nested objects. The curly bracing is also necessary.
Code: (Demo)
$products = [
(object)["item_id" => "89",
"name" => "Confiture de Myrtilles",
"product_id" => "737",
"meta_key" => "vmm_warehouse_sg_10783",
"meta_value" => "0"
],
(object)["item_id" => "89",
"name" => "Confiture de Myrtilles",
"product_id" => "737",
"meta_key" => "vmm_warehouse_sg_10782",
"meta_value" => "0"
]
];
$result = (object)[];
foreach($products as $product) {
if (!isset($result->{$product->item_id})) {
$result->{$product->item_id} = (object)[];
}
$result->{$product->item_id}->{$product->meta_key} = $product->meta_value;
}
var_export($result);
Output:
(object) array(
'89' =>
(object) array(
'vmm_warehouse_sg_10783' => '0',
'vmm_warehouse_sg_10782' => '0',
),
)
Alternatively, to generate the nested object structure, you could build an array of arrays, then use json_encode(), then json_decode() on the result.
If you want an array as output, that's easiest:
Code: (Demo)
$products = [
(object)["item_id" => "89",
"name" => "Confiture de Myrtilles",
"product_id" => "737",
"meta_key" => "vmm_warehouse_sg_10783",
"meta_value" => "0"
],
(object)["item_id" => "89",
"name" => "Confiture de Myrtilles",
"product_id" => "737",
"meta_key" => "vmm_warehouse_sg_10782",
"meta_value" => "0"
],
(object)["item_id" => "91",
"name" => "Poires Guyot (bio)",
"product_id" => "690",
"meta_key" => "_backorders",
"meta_value" => "no"
],
(object)["item_id" => "91",
"name" => "Poires Guyot (bio)",
"product_id" => "690",
"meta_key" => "_sold_individually",
"meta_value" => "no"
]
];
$result = [];
foreach($products as $product) {
$result[$product->item_id][$product->meta_key] = $product->meta_value;
}
var_export($result);
Output:
array (
89 =>
array (
'vmm_warehouse_sg_10783' => '0',
'vmm_warehouse_sg_10782' => '0',
),
91 =>
array (
'_backorders' => 'no',
'_sold_individually' => 'no',
),
)
I don't fully understand what are you trying to achieve, but I suppose you want associative array with id as the key and array of meta_key and meta_value as its value?
If so, then:
foreach ( $Products as $Product ) {
$Meta_products[$Product->item_id][$Product->meta_key] = $Product->meta_value;
}
Related
In the JSON file, there are multiple item based on the same product_id. I have to create multidimensional array based on product_id and items.
As per my sample php code, product_id is repeatedly listing. Results are printed in php code.
Expecting results are given below.
testData.json
"data": [
{
"product_id": "123456",
"item": "ZAD",
"time": "15:30",
"quantity": 1
},
{
"product_id": "24534"
"item": "REST"
"time": "5:30"
"quantity": 1
},
{
"product_id": "123456"
"item": "RAD"
"time": "10:30"
"quantity": 2
}
]
test.php
$json = file_get_contents('testData.json');
$d_data = json_decode($json, true);
$f_data = $d_data['data'];
foreach($f_data as $data) {
$result = [
$data['product_id'],
$data['item']
]
print_r($result);
/* Array(
[0] => 123456
[1] => ZAD
)
Array(
[0] => 123456
[1] => RAD
)
Array(
[0] => 24534
[1] => REST
)
*/
}
Expecting Result
123456
[
ZAD
[
"time" => "15:30",
"quantity" => 1
],
RAD
[
"time" => "10:30"
"quantity" => 2
],
],
24534
[
REST
[
"time" => "5:30"
"quantity" => 1
]
]
You just need to account for both product_id and item as sub-keys in the final array:
$result = [];
foreach($f_data as $data) {
$result[$data['product_id']][$data['item']] = [
$data['time'],
$data['quantity']
];
}
print_r($result);
Demo: https://3v4l.org/sf7om
I should note, if two items have the same product_id and same item, this code will only keep the last one. If that scenario applies to you, you just need to use the append mode ([]) of the array:
$result[$data['product_id']][$data['item']][] = [
$data['time'],
$data['quantity']
];
i am getting product data from API end.
there are two nested "data" in the incoming array.
i can list the products with foreach, but I can't reach a single element.
when I try a few methods, it returns errors like "array,object int". Where am I going wrong and how can I access its elements?
the method i'm trying now is this and i'm applying this process on the Laravel side.
{
"data": {
"data": [
{
"id": 101553,
"company_id": 730,
"category_id": 132288,
"brand_id": 39549,
"name": "Hh PRODUCT TEST",
"remote_category_id": "scarf",
"remote_brand_id": "bershka123",
"spu": "zb3940823904"
},
{
"id": 101554,
"company_id": 730,
"category_id": 132289,
"brand_id": 39549,
"name": "Hs PRODUCT TEST",
"remote_category_id": "scarf",
"remote_brand_id": "bershka123",
"spu": "zb3940823905"
}
],
"count": 175,
"search": {
"category_id": null,
"brand_id": null,
"company_id": null
},
"start": 0,
"length": 10
},
"error_code": 0,
"message": ""
}
Model:
public function getProducts($start =0, $length =10, $category_id =null, $brand_id=null, $spu=null, $name=null, $is_active=null, $id=null, $remote_brand_id = null, $remote_category_id=null)
{
$request = Http::withHeaders([
'Authorization' => 'Bearer '.$this->jwttoken,
'Content-Type' => 'application/json'
])->post($this->sandbox . 'products/search',[
"start" => $start,
"length" => $length,
"search" => [
"category_id" => $category_id,
"brand_id" => $brand_id,
"spu" => $spu,
"name" => $name,
"is_active" => $is_active,
"id" => $id,
"remote_brand_id" => $remote_brand_id,
"remote_category_id" => $remote_category_id
]
])->json();
return $request;
}
controller
$company_id = 100;
$products = (new Client($company_id))->getProducts();
foreach($products as $product){
foreach($product as $prd){
dump($prd);
}
}
Result:
0 => array:27 [
"id" => 101530
"company_id" => 730
"category_id" => 132047
"brand_id" => 39316
"name" => "Hs Test Shoe"
"remote_category_id" => "5a39b114f1ff6e42639e9e041cd002d6"
"remote_brand_id" => "617392d2b51dbba1a2e5561a3e4eefe7"
"spu" => "845504"
],
1 => array:36 [
"id" => 231303
"company_id" => 730
"product_id" => 101530
"supplier_id" => null
"remote_supplier_id" => null
"name" => "Hd Test Shoe"
"description" => "This is a test product."
"sku" => "2K4F9966WHITE42"
]
ErrorException :
foreach() argument must be of type array|object, int given
How do i get the correct loop format and elements?
You have to loop like this way
foreach($products["data"]["data"] as $product)
{
dump($product);
}
I have a nested collection that I want to transform, pulling some keys "up a level" and discarding some other keys.
Every item in the collection has an allergens property.
"allergens": [
{
"id": 2001,
"info": "Allergy advice",
"status": "does_contain",
"product_id": 71576,
"allergen_id": 1,
"allergen": {
"id": 1,
"name": "Celery"
}
},
{
"id": 2002,
"info": "Allergy advice",
"status": "may_contain",
"product_id": 71576,
"allergen_id": 11,
"allergen": {
"id": 11,
"name": "Peanuts"
}
}
],
I need to make each items allergens property, look like
"allergens": [
{
"id": 1,
"name": "Celery"
"status": "does_contain",
},
{
"id": 11,
"name": "Peanuts"
"status": "does_contain",
},
],
I've tried the following:
$collection = $collection->transform(function ($item, $key) {
$item->allergens = $item->allergens->map(function ($allergen) {
return [
'id' => $allergen->allergen->id,
'name' => $allergen->allergen->name,
'status' => $allergen->status,
];
});
return $item;
});
But it doesn't overwrite the allergens property
Since you're posting your collection as JSON, I reverse engineered what your actual collection would look like. Turns out, your transform() works fine as far as I can tell. Maybe that helps you to find differences between my and your collection which might lead you to your problem/solution:
$collection = collect([
(object)[
"allergens" => collect([
(object)[
"id" => 2001,
"info" => "Allergy advice",
"status" => "does_contain",
"product_id" => 71576,
"allergen_id" => 1,
"allergen" => (object)[
"id" => 1,
"name" => "Celery"
]
],
(object)[
"id" => 2002,
"info" => "Allergy advice",
"status" => "may_contain",
"product_id" => 71576,
"allergen_id" => 11,
"allergen" => (object)[
"id" => 11,
"name" => "Peanuts"
]
]
]),
]
]);
$collection = $collection->transform(function ($item, $key) {
$item->allergens = $item->allergens->map(function ($allergen) {
return [
'id' => $allergen->allergen->id,
'name' => $allergen->allergen->name,
'status' => $allergen->status,
];
});
return $item;
});
dd($collection);
Result:
Illuminate\Support\Collection {#1779 ▼
#items: array:1 [▼
0 => {#1791 ▼
+"allergens": Illuminate\Support\Collection {#1775 ▼
#items: array:2 [▼
0 => array:3 [▼
"id" => 1
"name" => "Celery"
"status" => "does_contain"
]
1 => array:3 [▼
"id" => 11
"name" => "Peanuts"
"status" => "may_contain"
]
]
}
}
]
}
I am trying to change an indexed array of arrays into a new array structure. My data is as follows:
$arr = array(
array( "year" => 1921, "name" => "bob" ),
array( "year" => 1944, "name" => "steve" ),
array( "year" => 1944, "name" => "doug" ),
array( "year" => 1921, "name" => "jim" ),
);
I would like to recreate a new array thats groups them into the same year. The best I can come up with is designating the year as the key so any row that has that year gets added to that key, but it's not the output that I'm looking for. What I need is how it's listed below.
"data": [
{
"year":"1921",
"names": [
{ "name":"bob" }, { "name":"jim"}
]
},
{
"year":1944",
"names": [
{ "name":"steve" }, { "name":"doug "}
]
}
You don't need to pre-extract the unique years nor use conditions within nested loops. Just push the data into the result set using temporary first-level keys, then remove the temporary keys when finished looping.
This ensures unique years, but allows names to be duplicated.
Code: (Demo)
$arr = [
["year" => 1921, "name" => "bob"],
["year" => 1944, "name" => "steve"],
["year" => 1944, "name" => "doug"],
["year" => 1921, "name" => "jim"],
];
foreach ($arr as $item) {
$result[$item['year']]['year'] = $item['year'];
$result[$item['year']]['names'][] = ['name' => $item['name']];
}
echo json_encode(
['data' => array_values($result)],
JSON_PRETTY_PRINT // for better visualization
);
Output:
{
"data": [
{
"year": 1921,
"names": [
{
"name": "bob"
},
{
"name": "jim"
}
]
},
{
"year": 1944,
"names": [
{
"name": "steve"
},
{
"name": "doug"
}
]
}
]
}
I have a script that expects the following output:
[{
"id": "288",
"title": "Titanic",
"year": "1997",
"rating": "7.7",
"genre": "drama, romance",
"od": "0"
}, {
"id": "131",
"title": "The Bourne Identity",
"year": "2002",
"rating": "7.9",
"genre": "action, mystery, thriller",
"od": "1"
}]
That does not look like well formatted json, as when I do this:
return new JsonResponse(array(
"id" => 288,
"title" => "Titanic",
"year" => "1997",
....
));
I am getting this:
{
"id": 288,
"title": "Titanic",
"year": "1997"
....
}
The plugin I am using is this, and it even has a $.getJson Function?!?
How would I change the output format?
its just missing its outer container.
try this:
return new JsonResponse( array( array(
"id" => 288,
"title" => "Titanic",
"year" => "1997"
)) );
this should output as:
[{"id":288,"title":"Titanic","year":"1997"}]
You have to include the items array into a parent one:
return new JsonResponse(array(
array(
"id" => 288,
"title" => "Titanic",
"year" => "1997",
....
),
array(
"id" => 288,
"title" => "Titanic",
"year" => "1997",
....
)
));
You have to put your data in another array to create an array of items. Just wrap the existing array in another array:
return new JsonResponse(array(
array(
"id" => 288,
"title" => "Titanic",
"year" => "1997",
....
)
));