Rails Activerecord last 5 records based on field value - ruby-on-rails

I want to fetch the last 5 records where transfer = something. Currently I'm using: Model.limit(5).order('id desc') but that shows the last 5 of Call.all. How can I express this by adding a where clause or specifying a particular value as part of the query?

Simply
Model.where(:transfer => 'something').order('id desc').limit(5)
But it might make more sense to order by created_at or updated_at instead of id.

Related

How to get the latest created object in ruby on rails [duplicate]

I was wondering if there is a way to find the newest record in a table in rails3?
Given a Post model, you could do #post = Post.order("created_at").last
(The reason I didn't just do a #post = Post.last is because that always defaults to sort by your primary key (usually id). Most of the time this is fine, but I'm sure there's a scenario where that could cause problems (e.g. setting custom IDs on records, database changes which affect the primary key sequencing/autonumbering, etc.). Sorting by the created_at timestamp ensures you are really getting the most recent record).
While dmarkow's answer is technically correct, you'll need to make an index on created_at or risk an increasingly slow query as your database grows.
If you know that your "id" column is an auto-increment primary key (which it likely is), then just use it since it is an index by definition.
Also, unless AREL is optimized to select only one record in a find(:last), you run the risk of making it select ALL records, then return you just the last one by using the "last()" method. More efficient is to limit the results to one:
MyModel.last(:order => "id asc", :limit => 1)
or
MyModel.first(:order => "id desc", :limit => 1)
you may run into ambiguity issues using created_at on a sufficiently high-traffic table.
eg. try:
INSERT INTO table (created_at) VALUES ( NOW() );
INSERT INTO table (created_at) VALUES ( NOW() );
..has the potential to have the same created_at, which only has 1 second of resolution. a sort would return them in no particular order.
you may be better off storing a microtime value and sorting on that.
Yes, you can use the method .last
So if your model is called Post then:
>> Post.last
=> #<Post ...>
Try, for a model named ModelName:
record = ModelName.last

PostgreSQL in Rails: sorting object by two date attributes in descending order

I have an index of active job positions. Currently, they're sorted by the most recent i.e. created_at. However, recently i've added in a renewal feature that updates a renewal_date attribute without updating the created_at.
What I want to achieve is to sort the list in descending order using both renewal_date and created_at.
jobs = Job.where(active: true).reorder("renewal_date DESC NULLS LAST", "created_at DESC")
With this code, the renewed job will always be at the top regardless of how many new jobs are created. How do I sort it so it checks for the date for both attributes and sorts it according to most recent?
Your code will order first by renewal_date with nulls at the end, and then will look at the created_at if two records have the same renewal_date.
I assume that what you want to do is something like "max(renewal_date, created_at)", which will take the "last modification date", or another custom way to compare the two fields.
If then, you can find your answer here : merge and order two columns in the same model
Job.where(active: true).reorder('GREATEST(renewal_date, created_at) DESC')
Let try a standard SQL, so it can work with all types of database:
Job.where(active: true).order('CASE WHEN renewal_date IS NULL THEN created_at ELSE renewal_date END DESC')

How to sort by an associated column in this active record query

I need a few queries sorted by an associated model. I have a list of Customers that I get and I need to make sure the customer list is sorted by the last Message they received. Here are the current queries:
#open_customers = #company.customers.open.includes(:last_received_message)
#your_customers = current_user.customers.includes(:last_message)
#sidebar_customers = current_company.customers.open_or_claimed.
where("user_id = ? OR user_id IS NULL", current_user.id).
order(aasm_state: :asc).includes([:last_received_message, :user])
these are three separate queries.
#open_customers needs to be sorted by the created_at of last_received_message
#your_customers needs to be sorted by the created_at of last_message
#sidebar_customers needs to be sorted by the created_at of last_received_message
thanks!
You might try checking out Section 14: scopes here: http://guides.rubyonrails.org/active_record_querying.html
Also this website has a course called Rails 4 Outlaws that does a great job teaching scopes: https://www.codeschool.com

Model.first does not retrieve first record from table

Model.first doesnot retrive first record from table. Instead it retrives any random record from table.
eg:
Merchant.first
Query
SELECT "merchants".* FROM "merchants" LIMIT 1
=> <Merchant id: 6, merchant_name: "Bestylish", description: "", description_html: "" >
Instead the query should be
SELECT "merchants".* FROM "merchants" ORDER BY "merchants"."id" ASC LIMIT 1;
Why it doesnot retrive the first record
Model.first will use the default sorting of your database.
For example. In Postgresql default sorting is not necessarily an id.
This seems to be default behaviour with Postgres, as some active-record versions do not add a default ordering to the query for first, while adding one for last.
https://github.com/rails/rails/issues/9885
PostgreSQL does not by default apply a sort, which is generally a good thing for performance.
So in this context "first" means "the first row returned", not "the first row when ordered by some meaningless key value".
Curiously "last" does seem to order by id.
It is defined here, in Rails 4, to order by primary key if no other order conditions are specified.
In Rails 3.2.11, it is as such:
def find_first
if loaded?
#records.first
else
#first ||= limit(1).to_a[0]
end
end
Without the order method, which will just apply the limit and then leave the ordering up to your database.
You need to apply the ordering yourself. Try calling Merchant.order('id ASC').first
It may be possible to automate this using default scopes in your model but I'm not sure about that.

Find the newest record in Rails 3

I was wondering if there is a way to find the newest record in a table in rails3?
Given a Post model, you could do #post = Post.order("created_at").last
(The reason I didn't just do a #post = Post.last is because that always defaults to sort by your primary key (usually id). Most of the time this is fine, but I'm sure there's a scenario where that could cause problems (e.g. setting custom IDs on records, database changes which affect the primary key sequencing/autonumbering, etc.). Sorting by the created_at timestamp ensures you are really getting the most recent record).
While dmarkow's answer is technically correct, you'll need to make an index on created_at or risk an increasingly slow query as your database grows.
If you know that your "id" column is an auto-increment primary key (which it likely is), then just use it since it is an index by definition.
Also, unless AREL is optimized to select only one record in a find(:last), you run the risk of making it select ALL records, then return you just the last one by using the "last()" method. More efficient is to limit the results to one:
MyModel.last(:order => "id asc", :limit => 1)
or
MyModel.first(:order => "id desc", :limit => 1)
you may run into ambiguity issues using created_at on a sufficiently high-traffic table.
eg. try:
INSERT INTO table (created_at) VALUES ( NOW() );
INSERT INTO table (created_at) VALUES ( NOW() );
..has the potential to have the same created_at, which only has 1 second of resolution. a sort would return them in no particular order.
you may be better off storing a microtime value and sorting on that.
Yes, you can use the method .last
So if your model is called Post then:
>> Post.last
=> #<Post ...>
Try, for a model named ModelName:
record = ModelName.last

Resources