Concatenate 2 integers to an integer MongoDB - mongodb

I have a scraped some sports data, which contains an id field that ideally I'd like to use as Mongo's "_id". It's event based data and the IDs are meant to be unique however there is a few cases where they are not. However each entry also has a match id value, which is unique. There is never duplicated event IDs for the same match id. I was looking for a way to concatenate the two fields to create a unique id value that I could then use as the "_id" but this doesn't seem possible. I tried using the $concat operation with $tostring however this results in values such as 54821.4e+09
For example, a document with match id 3181621 and event id 1339018347 using
{$project:{"new_id":{$concat:[{"$toString":"$matchId"},"",{"$toString":"$id"}]}}}
results in "new_id" : "3181621.33902e+09", when I would want it to be 31816211339018347

Related

What is the optimal way of querying array with a lot of objectIds

I have an array of MongoDB Object IDs which I want to send to my nodejs server in order to get the objects' data.
The problem is that this array contains hundreds of IDs and I am not sure how should I fetch and query it as concatenating it to the query string will not do as the maximal URL can have up to 2048 characters.
You can do the following things:
If records in DB ordered by _id
Send an array of Ids in the POST request or send Min and max Id only in the query parameter in the GET request.
Instead, query for individual Id(objectId) or doing {$in : [ObjectId( )... ObjectId.....]} do as mentioned in below point.
Using min and max id from an array, query DB like this:
User.find({"_id":{$lte: idmax,$gte:idmin}})
If records are not ordered on _id:
User.find({"_id":{$in:[_id1,id_2.....]})
PS: Learn more about range queries.
The relationship between the order of ObjectId values and generation
time is not strict within a single second. If multiple systems, or
multiple processes or threads on a single system generate values,
within a single second; ObjectId values do not represent a strict
insertion order. Clock skew between clients can also result in
non-strict ordering even for values, because client drivers generate
ObjectId values, not the mongod process. So if this is a case you will
have to query using in operator {$in : [ObjectId( ). ObjectId.....]}
Long story short: If ids are not in the order in DB you will have to use
the in operator because otherwise, the range query will fetch
extra-record.

Does length of indexed field matter while searching?

The chat app schema that I have is something like below.
1. conversations {participants[user_1, user_2], convsersation_id}
2. messages {sender: user_1, sonversation_id, timestamps}
I want to map this relationship using existing _id:ObjectId which is already indexed.
But if I want to get all conversation of user_1 I have to first search in which conversation that user is involed and get that conversation's _id and again search for the messages in messages using that conversation _id.
So my questions are -
Does length of indexed field (here _id) matters while searching?
Should I create another shorter indexed fields?.
Also if there is any better alternative schema please suggest.
I would suggest you to maintain the data as sub documents instead of array. The advantage you have is you can build another index (only) on conversation_id field, which you want to query to know the user's involvement
When you maintain it as array, you cannot index the converstaion_id field separately, instead you will have to build a multi key index, which indexes all the elements of the array (sender and timestamps fields) which you are never going to use for querying and it also increases the index size
Answering you questions:
Does length of indexed field (here _id) matters while searching? - Not really
Should I create another shorter indexed fields? - Create sub-document and index converstaion_id
Also if there is any better alternative schema please suggest. - Maintain the array fields as sub-documents

Find documents with a certain field value only when another field value is a given string

I'm using this php package to make queries - https://github.com/jenssegers/laravel-mongodb
The situation is, there are two fields, user_id and post_status among others. I want to retrieve all the documents in that collection, but when post_status field value is draft, that should be retrieved only when user_id is a given string. The idea is, only logged in user finds their drafted posts among other posts.
I'm having hard time finding any solution for this problem. The app is still not in production. If I should store data is some different manner, that is an option as well.
Find documents with a certain field value only when another field value is a given string
The question your are framing is simply convert into a and query, how let's see it
when another field value is a given string
This means that you have some result sets and you need to filter out when user_id match with some string. i.e some result sets and user_id = <id>
Now consider the first part of the sentence Find documents with a certain field value
This means you are filtering the records with some values i.e "status" = "draft" and whatever result will come and want again to filter on the basis of user_id = <id>
So finally you will end-up with below query:
db.collectionName.find({"status":"draft", "user_id": "5c618615903aaa496d129d90"})
Hope this explanation will help you out or you can rephrase your question I will try to modify by ans.

Can mongo document ID format be customised?

I would like to encode some meaning behinds first N characters of every document ID i.e. make first three characters determine a document type sensible to the system being used in.
You can have a custom _id when you insert the document. If the document to be inserted doesn't contain _id, then MongoDB will insert a ObejctId for you.
The _id can be of any type but keeping it uniform for all the documents makes sense if you are accessing from application layer.
You can refer one of the old questions at SO - How to generate unique object id in mongodb

Mongodb query forward from username X

I have problem whit long Mongo find results. Example how can i start query starting from _id X
to forward Example I know I have document where is 1000 users details I know there is user called Peter in list I can make query Users.find({userName: "Peter"}) and get this on user _id but how I can get all users also after this with out I need return JSON from above "Peter"
With the little amount of information you have given, You need to do this in two steps:
Get the id of the first record that matches the name "peter".
db.test.findOne({"userName":"Peter"},{"_id":1});
Returns one document that satisfies the specified query criteria. If
multiple documents satisfy the query, this method returns the first
document according to the natural order which reflects the order of
documents on the disk. In capped collections, natural order is the
same as insertion order.
Once you have the id of the record with peter, you can retrieve the records with their id > the id of this record.
db.test.find({"_id":{$gte:x}});
Where, x is the id of the first record returned by the first query.