Elastic search, prevent one user clogging up all the results - elasticsearch

i have a campaigns that belong to users.
so my documents look something like this
campaign_id:1
user_id:1
date_created: 1234567890
now i want to show a list of campaigns sorted by newest. but right now if one user creates 100 campaigns my whole results for the first 4 pages will be the campaigns for this user.
What i am looking for is to spread out the campaigns so that it looks better
for example, if i have documents belonging to these user_ids
3,3,3,2,2,1,1,1,1,1,1,1,1,1
a query sorted by date_created will return me
1,1,1,1,1,1,1,1,2,2,3,3,3
what im looking for is this
1,2,3,1,2,3,1,3,1,1,1,1,1,1,1
user 1 is shown on top, then the latest of user 2 and 3, then we show the second latest of user 1,2,3 etc until user 2 and 3 have no documents left and all others from user 1 are at the bottom.
help?

Related

How to make query both to parent and child index?

I got parent index users and child purchase. Purchase has field purchase_count it is number of purchase made by user, for example first purchase of some user will be with purchase_count = 1, second with 2 etc.
I want to make query to get total number of users, number of users who had first purchase, number of users who had second etc. For example All: 100, 1: 10, 2: 6, 3: 3 etc..
I know how to do it in two requests, first get count of all users next term aggregation of purchases based on purchase_count field, but can I do it somehow in single query?
There is a datatype in Elasticsearch called parent-join or parent-child previously: https://www.elastic.co/guide/en/elasticsearch/reference/current/parent-join.html
That datatype needs to be in a single index. There are no joins across indices in Elasticsearch.
You probably want to look into parent-join for your usecase, but you'll have to restructure your data to reside in a single index.

Complex search query from 2 documents

I'm new to Elasticsearch and I need to execute a complex query, but I need some help.
Here is my use case:
I would like to recommend a new place to each of my users everyday.
However:
The place must be opened this week day
The chosen place must be near of the user (closer places have higher score)
The place should not be one of the last 10 places a user have already been/suggested (if a place has already been visited by a user in his last 10 visits, this place should have a lower score)
My first guess is to have 2 documents types as follow:
user_history
user_id
place_id
date
place
place_id
opening_days (array with week days the place opens)
location geo position of the place
Given a user with position [lat, lon] and id user_1, what could be the search query to execute to retrieve X places sorted by score? (better score is near of user and not in the 10 last places a user have already been).
This query seems to be a basic but I can't figure out how to "mix" data from user_history and from place to get places I want.
But that's not all!
With this query, if I want to attribute to each user a place I need 3 steps:
retrieve all users (with their position)
for each user, search for the best place
once I have this place, add it to the user_history
This seems very time consuming task. Is it possible to simplify it with less Elasticsearch queries?
For instance, having something like this:
retrieving for each user his best place (with 1 query, search for all users and find them the best place)
add the place to the history
Or event better:
retrieving for each user his best place and add it to the history (with 1 query, perform all the 3 tasks above)
I don't know if it's possible to create queries that complex. That's why I need your help to tell me if it's possible and how it could be accomplished.

Parse Querying Limit

If I have a PFQuery that will search through every user but I limit the results to 3 users, will that query search through every user and then give me 3 users? Or will the query pause/stop once 3 people have been found?
Thanks!
The query will stop searching once it finds what you set as your PFQuery's .limit.
And if you want to have pages of three users, you can use the .skip property, e.g. .skip = pageNumber * 3.

Google Sheets For Filtered Drop Down

I have two sheets: CONTACTS and UPDATES.
On the CONTACTS sheet there are 2 columns: COMPANY and NAME. If I have 10 contacts at a company, then there will be 10 rows with the same company in column 1, and the names of the 10 people in column 2. Now of course there's a lot of companies and names on this list.
On the UPDATES page, column 1 is a drop down that lets me select the name of the company. In column 2 I want to have a pull down that filters and shows me only the people in the company that's in column 1.
I've searched quite a bit and while I have found things that are similar, none of the tips are quite right / work for my use case.
Is there an easy way to do this?
Thanks for your help!
You can use UNIQUE + FILTER to filter the results, but that won't give you the a dropdown. For a filtered dropdown, you can use the formula to get the filtered list and then use that as your range.
For example, in your CONTACTS tab, add a new column FilteredList, with this formula in the first row:
=unique(filter(B:B,A:A=E1))
where B:B is the NAME column, A:A is the COMPANY column and E1 is where you select the company name on the UPDATES page.
Now, instead of making the NAMES list as your valid entries, set it to FilteredList.

How do I do a inner query in ElasticSearch with an outer 'Sort'

I'd like to achieve the following in ElasticSearch. I can mostly get the correct results, the problem is that I can't get the ordering of the final results list.
SELECT User, ScanDate, TotalSize FROM
[SELECT User, ScanDate, TotalSize FROM ElasticSearch
GROUP BY User ORDER BY ScanDate]
ORDER BY TotalSize LIMIT 10
Essentially, what I'm trying to do is to:
Get the Top 10 Users based on the TotalSize from their most recent Scan.
I can get the data (using aggregates and sub aggregates of Max). But, I'm then struggling to get the final ordering - and otherwise I'd have to do this the code that consumes this data, which I'd really not have to do.
Given the data:
Rich
ScanDate:1, TotalSize:27
ScanDate:2, TotalSize:3
ScanDate:3, TotalSize:9
Steve
ScanDate:2, TotalSize:2
ScanDate:5, TotalSize:1
John
ScanDate:1, TotalSize:50
I want an ordered result of:
John (ScanDate:1, TotalSize:50)
Rich (ScanDate:3, TotalSize:9)
Steve (ScanDate:5, TotalSize:1)
The events that are submitted to ElasticSearch look like this:
{"User":"Rich","ScanDate":1,"TotalSize":27,"Type":"ScanEvent"}
TotalSize is a LONG.
ScanDate is actually a timestamp.
User is a STRING (NOT_ANALYZED).
https://www.elastic.co/guide/en/elasticsearch/reference/current/search-request-sort.html
https://www.elastic.co/guide/en/elasticsearch/guide/current/nested-sorting.html
I guess this might help in what you are looking..

Resources