Unfortunately, I cannot use positional operators since there is a bug that doesn't allow deeper than 1 embedded document: https://jira.mongodb.org/browse/SERVER-831
So this wont work (using the Mongodb Ruby driver):
stat_profile.update({ profile_id: profile.id, providers: { '$elemMatch' => { provider_name: 'foo', dates: { '$elemMatch' => { date: 20130911, relationships: { '$elemMatch' => { relationship_type: 'friend' } } } } } } },
{ '$set' => { 'providers.$.dates.$.relationships.$.ids' => [1,2,3] } })
Given the following collection. Relationships is embedded in dates, dates is embedded in providers.
How do I update the ids field?
{
"_id" => BSON::ObjectId('523048983858f61767000008'),
"profile_id" => 3,
"providers" => [
[0] {
"provider_name" => "foo",
"dates" => [
[0] {
"date" => 20130911,
"relationships" => [
[0] {
"relationship_type" => "acquaintance",
"count" => 0
},
[1] {
"relationship_type" => "friend",
"count" => 0,
"males_count" => 0,
"females_count" => 0,
"top_ten_countries" => [],
"ids" => []
}
]
}
]
}
]
}
Related
db.getCollection('Subscriber').find({$and:[{"registerFrom":{$exists:false}},{"googleRegistrationId":{$exists:true}},{"isGuest":"false"}]})
how to write the above query in Perl please help this.I am getting different results on this when execute on perl
i have written like this in perl
my $Subscriber2 = $Subscriber->find({'$and' =>[{dateOfJoining => {'$gt' => $date}},{registerFrom => { '$exists' => 'false'}},{googleRegistrationId => {'$exists' => 'true'}},{isGuest => 'false'}]})->fields({ _id => 1,streamzCampaigns => 1});
I am not getting the same results as when executing in perl.How to use $exits of mongoDB in Perl.Please help on this one.
The two suspicious bits I see are that you've quoted "true" and "false" -- which make those strings, not boolean values -- and I wonder what you're using for $date, since you don't have that in your shell example.
Here is what you wrote, formatted nicely:
my $Subscriber2 = $Subscriber->find(
{
'$and' => [
{ dateOfJoining => { '$gt' => $date } },
{ registerFrom => { '$exists' => 'false' } },
{ googleRegistrationId => { '$exists' => 'true' } },
{ isGuest => 'false' }
]
}
)->fields( { _id => 1, streamzCampaigns => 1 } );
For the booleans, you should use the boolean.pm module:
use boolean;
my $Subscriber2 = $Subscriber->find(
{
'$and' => [
{ dateOfJoining => { '$gt' => $date } },
{ registerFrom => { '$exists' => false } },
{ googleRegistrationId => { '$exists' => true } },
{ isGuest => false }
]
}
)->fields( { _id => 1, streamzCampaigns => 1 } );
As the title suggests, I am upgrading to ES5. My original ES query looked like:
my $response = $elastic->do_request_new(
{
query => {
filtered => {
filter => {
or => [
{ term => { _type => { value => "some_val1" } } },
{ term => { _type => { value => "some_val2" } } },
]
},
query => {
query_string => {
query => $qstring,
rewrite => "scoring_boolean",
analyze_wildcard => "true",
}
}
}
},
sort => [ qw(_score) ],
size => 50,
},
);
My updated looks like:
my $response = $elastic->do_request_new(
{
query => {
bool => {
should => [
{ term => { _type => { value => "some_val1" } } },
{ term => { _type => { value => "some_val2" } } },
],
must => {
query_string => {
query => $qstring,
rewrite => "scoring_boolean",
analyze_wildcard => "true",
}
}
}
},
sort => [ qw(_score) ],
size => 50,
},
);
However, upon searching for exact strings in my elastic database, I am returning zero results:
{
"took" : 3,
"timed_out" : false,
"_shards" : {
"total" : 5,
"successful" : 5,
"failed" : 0
},
"hits" : {
"total" : 0,
"max_score" : null,
"hits" : [ ]
}
}
Any ideas about what might be happening? My guess is I have my query structure wrong. Thanks!
Update: The following fixed query:
my $response = $elastic->do_request_new(
{
query => {
bool => {
must => [
{
query_string => {
query => $qstring,
rewrite => "scoring_boolean",
analyze_wildcard => "true",
},
}
],
filter => {
bool => {
should => [
{ term => { _type => { value => "some_val1" } } },
{ term => { _type => { value => "some_val2" } } },
],
},
},
},
},
sort => [ qw(_score) ],
size => 50,
},
);
I created mongodb query which I have to use in laravel controller.
My query is
db.PMS.aggregate([
{ $match: { "PanelID": "A00898" } },
{
$project: { EventTS: 1, MainsPower: 1, }
},
{
$unwind: {
path: "$MainsPower",
includeArrayIndex: "arrayIndex",
preserveNullAndEmptyArrays: true
}
},
{
$project: {
MainsPower: 1,
timestamp: {
"$add": [
"$EventTS",
{ "$multiply": [ 60000, "$arrayIndex" ] }
]
}
}
}
]);
I tried to use this query in a laravel function but I am little confused. Please help me how to implement this query in laravel.
Perform raw expressions on the internal MongoCollection object to run the aggregation:
$result = DB => collection('PMS')->raw(function ($collection){
return $collection->aggregate(array(
array( '$match' => array( "PanelID" => "A00898" ) ),
array( '$project' => array( 'EventTS' => 1, 'MainsPower' => 1 ) ),
array(
'$unwind' => array(
'path' => "$MainsPower",
'includeArrayIndex' => "arrayIndex",
'preserveNullAndEmptyArrays' => true
)
),
array(
'$project' => array(
'_id' => 0,
'MainsPower' => 1,
'timestamp' => array(
"$add" => array(
"$EventTS",
array( "$multiply" => array( 60000, "$arrayIndex" ) )
)
)
)
)
));
});
i'm trying to run query with unwind. (aggregation)
the problem is that when i'm running unwind on an empty array I get empty result.
I know that this is a problem:
If the array holds an empty array ([]) in an input document, the
pipeline ignores the input document and will not output documents for
that input document. (from MongoDB docs)
is there an option that i can run 'unwind' only when the array i'm trying to unwind isn't empty?
EDIT:
$match = [
'_id' => ['$in' => $ids]
];
$project = [
'name' => true,
'sum1' => true,
'array1' => true,
'array2' => true,
'array3' => true
];
$group = [
'_id' => '$name',
'sum1' => ['$sum' => '$sum1'],
'array1' => ['$push' => '$array1'],
'array2' => ['$push' => '$array2'],
'array3' => ['$push' => '$array3']
];
$query = [
['$match' => $match],
['$project' => $project],
['$group' => $group],
['$unwind' => '$array1'],
['$unwind' => '$array2'],
['$unwind' => '$array3']
];
$ret = mongo_get_db()
->selectCollection("collection")
->aggregate($query);
EDIT2:
{
name: ‘name1’
sum1: 2
array1:
[
{
id: 111
name: 222
}
]
array2: []
array3: []
}
{
name: ‘name1’
sum1: 10
array1:
[
{
id: 122
name: 333
}
]
array2: []
array3: []
}
RESULT:
{
name: ‘name1’
sum1: 12
array1:
[
{
id: 111
name: 222
}
{
id: 122
name: 333
}
]
array2: []
array3: []
}
tnx :)
You could try a $match operator prior to the $unwind that filters documents which have the array that has at least an element, using the logic that there exists at least the first element indexed 0 in the array (with the dot notation):
{ $match: { "array_field.0": { $exists: true } } };
Why not simply check if the array is empty?
if(myArray.length === 0) { /* call your code here */ }
I have this structure:
{
"user" => "xxxx",
"position" =>
{
"A1" => { "state" => 'It', region=>"LOM" etc etc..},
"A2" => { .... },
"A3" => { .... },
....
"An" => { .. }
}
}
insert is ok. but update return this error:
not a reference at /usr/local/lib/perl/5.12.4/MongoDB/Collection.pm line 376
My update is:
$tbl->update({
{ _id => MongoDB::OID->new(value => "$id") },
{ '$set' =>
{
"position" =>
{
"A1" => { "state" => "En" }
}
}
}
});
Where I wrong?
Thks!
I check syntax of update source of MongoDB::Collection
syntax update
update (\%criteria, \%object, \%options?)
inside MongoDB::Collection method update
sub update {
my ($self, $query, $object, $opts) = #_;
...
}
but you pass only 1 parameter.
$tbl->update(
{ # 1st anonymous hash
{ _id => MongoDB::OID->new(value => "$id") },
{ '$set' => {
"position" => {
"A1" => { "state" => "En" }
}
}
}
});
So I advice you figure out with passed parameters to method update.