how to create blank embedded document in mongodb by php - php

I want to initialize an object in mongodb like this
{"_id":"123","name":"JACK","data":{}}
array and map is the same thing in php, so when I save this
$a = [ 'name': 'JACK', 'data': [] ]
I got this
{ "_id": "123", "name": "JACK", "data": [] }
Question: how to create blank embedded document in mongodb by php
there are to different document
{ "_id": "123", "name": "JACK", "data": {} }
{ "_id": "123", "name": "JACK", "data": [] }
the same command in MongoDB shell will do different thing
db.test.update( { "name": "JACK" }, { "$set": { "data.5": 1 } } )

If you are beginning PHP with mongodb, you may want to take a look at this
If you want to represent this:
{
"_id":"123",
"name":"JACK",
"data":{}
}
You could do this in PHP:
$emptyObj = new \stdClass();
$doc = array(
'_id' => '123',
'name' => 'JACK',
'data' => $emptyObj
);

Related

php echo from a start point to a end point

I have built a php site that takes code from a page using GET, and then echos it to the current page, but it exports text like this,
{ "selection13": [ { "name": "L" }, { "name": "100%\nA" } ], "selection7": [ { "name": "S" }, { "name": "100%\nA" } ], "selection8": [ { "name": "SS" }, { "name": "100%\nA" } ], "selection9": [ { "name": "SP" }, { "name": "100%\nA" } ], "selection10": [ { "name": "P" }, { "name": "100%\nA" } ], "selection11": [ { "name": "A" }, { "name": "100.00%\nA+" } ], "selection12": [ { "name": "H", "selection5": [ { "name": "T }, { "name": "100.00%\nA+" } ] }, { "name": "100.00%\nA+", "selection5": [ { "name": "T" }, { "name": "100.00%\nA+" } ] } ] }
I need to organizes it in to categorizes like, {L},{100%), here is the code I am currently using,
<?php
$params = http_build_query(array(
"api_key" => "()",
"format" => "json"
));
$result = file_get_contents(
'(url)'.$params,
false,
stream_context_create(array(
'http' => array(
'method' => 'GET'
)
))
);
echo gzdecode($result);
?>
Your script is outputting JSON but there appears to be a few issues with the data itself that need to be addressed first.
The next to the last "name": "T is missing a closing quote.
Section 12 has an inconsistent organization compared to the other sections. Can a section be a child of another section or is this an error?
"selection11": [
{
"name": "A"
},
{
"name": "100.00%\nA+"
}
],
"selection12": [
{
"name": "H",
"selection5": [
{
"name": "T"
},
{
"name": "100.00%\nA+"
}
]
},
{
"name": "100.00%\nA+",
"selection5": [
{
"name": "T"
},
{
"name": "100.00%\nA+"
}
]
}
]
These 2 issues need to be fixed in the JSON data you are retrieving first.
From there, the best way to reorganize this is to convert it to an array using json_decode.
$json = gzdecode($result);
$resultArray = json_decode($json);
I can't tell from your question exactly how you want to reorganize the data but use one or more of the builtin array functions to get the data in the structure you want. If you need to output it in JSON, use json_encode on the manipulated array to get the final data format. More specific help can be provided if you can be more clear on want output structure you are looking for and the format (does it need to be JSON or something else).

PHP - Slice nested array

I have two nested arrays with different length. I want to make length of second array as per first array, see below examples to get idea. Just remove all those items which don't exist in first array. Sometime second array has more values then first array, in this case my tree structure breaks.
These arrays are nested array so simple array_slice not working.
Here are the structure of array.
First Array
"1": {
"id": "1",
"username": "username",
"children": [
{
"id": "-1",
"username": "NULL",
"children": [
{
"id": "-1",
"username": "NULL",
"children": [
{
"id": "-1",
"username": "NULL",
"children": []
}
]
}
]
}
]
}
Second Array
"157": {
"id": "157",
"username": "test1",
"children": [
{
"id": "158",
"username": "test1",
"children": [
{
"id": "159",
"username": "test2",
"children": [
{
"id": "160",
"username": "test3",
"children": []
},
{
"id": "160",
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": []
}
]
}
]
},
{
"id": "160",
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": [
{
"id": "159",,
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": [
{
"id": "161",
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": []
}
]
}
]
}
]
}
Expected Output
"157": {
"id": "157",
"username": "test1",
"children": [
{
"id": "158",
"username": "test1",
"children": [
{
"id": "159",
"username": "test2",
"children": [
{
"id": "160",
"username": "test3",
"children": []
},
]
}
]
},
]
}
I am trying this method, but it is not working.
$firstCount = (array_map('count', $actualTree));
$secondCount = (array_map('count', $emptyTree));
$chunk = array_slice($actualTree, 0 , $second[$this->userId], true);
Use Case
The thing which I want to do is that remove those array childrens completely which are not exists in first array. I am building a binary tree upto three levels. First array already has a binary tree with empty values. The second array is data that is coming from the database, and I am simply replacing empty data with the actual data using array_replace. This is working good until second array has more values then first array. So to make it working I have to remove those extra elements.
Could anyone please help me to make there length same. Any help will be appreciated.
Thanks in advance.
A Stack Overflow miracle has occurred... I got a recursive snippet to work on the first pass! Usually it takes me a good hour or two to write something that works.
I don't know if I can make it any tighter/better OR if it will fail on any fringe cases, but:
it works for your sample input
it is midnight for me, I'm tired, and I have to work in the morning
Effectively, it synchronously & recursively iterates each array and stores each level of the entry array to the output array so long as the same level keys exists in the structure array.
Code: (Demo)
function truncateRecursive($structure, $entry) {
$output = [];
while (($structureKey = key($structure)) !== null && ($entryKey = key($entry)) !== null) {
$output[$entryKey] = !is_array($entry[$entryKey])
? $entry[$entryKey]
: truncateRecursive($structure[$structureKey], $entry[$entryKey]);
unset($structure[$structureKey], $entry[$entryKey]);
}
return $output;
}
var_export(truncateRecursive($structure, $entry));
Output:
array (
157 =>
array (
'id' => '157',
'username' => 'test1',
'children' =>
array (
0 =>
array (
'id' => '158',
'username' => 'test1',
'children' =>
array (
0 =>
array (
'id' => '159',
'username' => 'test2',
'children' =>
array (
0 =>
array (
'id' => '160',
'username' => 'test3',
'children' =>
array (
),
),
),
),
),
),
),
),
)

Using "aggregate" to combine a list of all subdocuments that match query?

I'm trying to use a PHP mongo library to "aggregate" on a data structure like this:
{
"_id": 100,
"name": "Joe",
"pets":[
{
"name": "Kill me",
"animal": "Frog"
},
{
"name": "Petrov",
"animal": "Cat"
},
{
"name": "Joe",
"animal": "Frog"
}
]
},
{
"_id": 101,
"name": "Jane",
"pets":[
{
"name": "James",
"animal": "Hedgehog"
},
{
"name": "Franklin",
"animal": "Frog"
}
}
For example, if I want to get all subdocuments where the animal is a frog. Note that I do NOT want all matching "super-documents" (i.e. the ones with _id). I want to get an ARRAY that looks like this:
[
{
"name": "Kill me",
"animal": "Frog"
},
{
"name": "Joe",
"animal": "Frog"
},
{
"name": "Franklin",
"animal": "Frog"
}
]
What syntax am I supposed to use (in PHP) to accomplish this? I know it has to do with aggregate, but I couldn't find anything that matches this specific scenario.
You can use below aggregation. $match to find documents where array has a value of Frog and $unwind the pets array. $match where document has Frog and final step is to group the matching documents into array.
<?php
$mongo = new MongoDB\Driver\Manager("mongodb://localhost:27017");
$pipeline =
[
[
'$match' =>
[
'pets.animal' => 'Frog',
],
],
[
'$unwind' =>'$pets',
],
[
'$match' =>
[
'pets.animal' => 'Frog',
],
],
[
'$group' =>
[
'_id' => null,
'animals' => ['$push' => '$pets'],
],
],
];
$command = new \MongoDB\Driver\Command([
'aggregate' => 'insert_collection_name',
'pipeline' => $pipeline
]);
$cursor = $mongo->executeCommand('insert_db_name', $command);
foreach($cursor as $key => $document) {
//do something
}
?>

Multi update with $set and php Mongo

I'm trying to update multiple items in a collection using the update() function with multi=true param on mongolab platform. The problem is only the first item in the collection is updated.
The collection:
{
"_id": {
"$oid": "5454b446e4b02a012c939a0a"
},
"value": "1234",
"name": "first"
},
{
"_id": {
"$oid": "5454b446e4b02a012c939a0a"
},
"value": "1234",
"name": "second"
}
Script code:
$db->collection->update(
array('value' => '1234'),
array('$set' => array(
'name' => 'example name',
)),
array('multi' => true)
);
Result:
{
"_id": {
"$oid": "5454b446e4b02a012c939a0a"
},
"value": "1234",
"name": "example name"
},
{
"_id": {
"$oid": "5454b446e4b02a012c939a0a"
},
"value": "1234",
"name": "second"
}
The update() function accepts only three arrays as arguments.
Hi Yogesh,
I think your query should be:
db.collectionName.update({"value":"1234"},{$set:{"name":"example name"}},{'upsert':true, 'multiple': true});
The corresponding PHP codes would be:
<?php
$m = new MongoClient(); //connects to local mongo
$db_name = 'ri'; //replace database name you want to work with
$collection_name = 'brand_graph'; //replace collection name you want to work with
$select = $m->selectDB($db_name)->selectCollection($collection_name);
$where_array = array(
'value' => 1234
);
$update_data = array(
'$set' => array(
'name' => 'example name'
)
);
$options = array(
'upsert' => true,
'multiple' => true
);
$select->update($where_array, $update_data, $options);
?>
I hope this is what your were looking for.
I write below mongo query which update multiple documents but , I don't know how to convert this in PHP code but for reference you should use this query
db.collectionName.update({"value":"1234"},{$set:{"name":"example name"}},true,true)

Creating a PHP object with out the use of a key?

I've got a request to present the data in the following format as a JSON feed:
{
"id": "123",
"info": {
"code": "ZGE",
"description": "test1",
"type": "AVL",
"date": "09/08/2012"
}
},
{
"id": "456",
"info": {
"code": "ZDN",
"description": "test2",
"type": "CLR",
"date": "16/02/2012"
}
}
However in my PHP code, I think I need to have a key itterator - but I end up with this format:
{
"0": {
"id": "123",
"info": {
"code": "ZGE",
"description": "test1",
"type": "AVL",
"date": "09/08/2012"
}
},
"1": {
"id": "456",
"info": {
"code": "ZDN",
"description": "test2",
"type": "CLR",
"date": "16/02/2012"
}
}
}
Any ideas on how to build the first data set with out having the index iterator?
simple create an array of objects, no need for the key (notice the [ ] surrounding your list)
json.txt
[{
"id": "123",
"info": {
"code": "ZGE",
"description": "test1",
"type": "AVL",
"date": "09/08/2012"
}
},
{
"id": "456",
"info": {
"code": "ZDN",
"description": "test2",
"type": "CLR",
"date": "16/02/2012"
}
}]
example.php
<?php
$data = json_decode(file_get_contents('./json.txt'));
?>
It can be built like this:
$arr = array(
array(
'id' => 123,
'info' => array(
'code' => 'ZGE',
'description' => 'test1',
'type' => 'AVL'
)
),
array(
'id' => 456,
'info' => array(
'code' => 'ZDN',
'description' => 'test2',
'type' => 'CLR'
)
)
);
echo json_encode($arr);
Outputs
[
{
"id": 123,
"info": {
"code": "ZGE",
"description": "test1",
"type": "AVL"
}
},
{
"id": 456,
"info": {
"code": "ZDN",
"description": "test2",
"type": "CLR"
}
}
]
the JSON format you've specified in the first example (ie the requested format) is not valid JSON.
A valid JSON string must evaluate to a single Javascript object; the example you've given evaluates to two Javascript objects, separated by a comma. In order to make it valid, you would need to either enclose the whole thing in square brackets, to turn it into a JS array or enclose it in curly braces, and give each of the two objects a key.
The PHP code you've written is doing the second of these two options. It is therefore generating valid JSON code, about as close to the original request as could be expected while still being valid.
It would help if you'd shown us the PHP code that you've used to do this; without that, I can't really give you advice on how to improve it, but if you want to switch to the square bracket notation, all you need is to put your PHP objects into an unkeyed array, and json_encode() should do it all for you; you shouldn't need to use a keyed array or an iterator for that.
The only reason json_encode should produce the output you're seeing is adding another named key to the array that you're passing to json_encode, by default it should work as you want:
$json = '[
{
"id": "123",
"recall_info": {
"code":"ZGE",
"description": "test1",
"type": "AVL",
"date": "09/08/2012"
}
},
{
"id": "123",
"recall_info": {
"code": "ZDN",
"description": "test2",
"type": "CLR",
"date": "16/02/2012"
}
}
]';
$php = array(
(object) array(
'id' => '123',
'recall_info' => (object) array(
'code' => 'ZGE',
'description' => 'test1',
'type' => 'AVL',
'date' => '09/08/2012'
)
),
(object) array(
'id' => '123',
'recall_info' => (object) array(
'code' => 'ZGE',
'description' => 'test2',
'type' => 'CLR',
'date' => '16/02/2012'
)
)
);
var_dump(json_encode($php));

Categories