Como obter o registro criado hoje pelo rails activerecord?


Respostas:


220
Post.where(created_at: Time.zone.now.beginning_of_day..Time.zone.now.end_of_day)

PS: Esta resposta foi modificada porque a resposta de Harish Shetty era melhor do que a minha. Como minha resposta é aceita. Eu atualizei esta resposta para o suporte da comunidade


4
Pode-se fazer Post.where (created_at: Time.zone.now.beginning_of_day..Time.zone.now.end_of_day)
— Rafael Oliveira

1
Não adianta verificar se algo foi criado antes do final de hoje (já que o amanhã ainda não aconteceu).
— jakeonrails

4
Embora Post.where("created_at >= ?", Time.zone.now.beginning_of_day)seja muito inteligente, eu endossaria Post.where(created_at: Time.zone.now.beginning_of_day..Time.zone.now.end_of_day). Há um ponto em fazer de uma forma que você possa manipular o tempo. Por exemplo, se você estiver testando, provavelmente irá manipular o tempo e então a primeira opção não funcionará. Você deseja evitar esse tipo de possível falha futura que provavelmente levará algum tempo de depuração.
— lucasarruda

123

Eu sei que esta pergunta tem uma resposta aceita. A solução sugerida na resposta aceita pode causar problemas de desempenho quando o tamanho da mesa aumenta.

Normalmente, se você realizar pesquisas com base na created_atcoluna, adicione um índice na tabela em seu arquivo de migração.

add_index :posts, :created_at

Agora, para consultar os registros criados hoje:

Rails 3/4

Post.where("created_at >= ?", Time.zone.now.beginning_of_day)

Para pesquisar postagens criadas em um dia específico.

Post.where(:created_at => (date.beginning_of_day..date.end_of_day))

--------- OU -------------

Adicione um método estático ao seu modelo

class Post < ActiveRecord::Base
  def self.today
    where("created_at >= ?", Time.zone.now.beginning_of_day)
  end
end

Post.today #returns posts today

Rails 2

Post.all(:conditions => ["created_at >= ?", Time.zone.now.beginning_of_day])

--------- OU -------------

Adicione um named_scope ao seu modelo

class Post < ActiveRecord::Base    
  named_scope :today, lambda { 
    {
      :conditions => ["created_at >= ?", Time.zone.now.beginning_of_day]
    }
  }
end

Post.today #returns posts today

1
Excelente ponto sobre indexação. Só queria esclarecer que o scopeexemplo neste post é apenas para Rails 3, já que parece que está sob o título Rails 2. No Rails 2, você precisaria usar named_scopeao invés de scope. Além disso, no Rails 3, você poderia usar de forma equivalente um método de classe def self.today where("created_at >= ?", Time.now.beginning_of_day) end que provavelmente é mais limpo do que usar um escopo neste caso, já que permite que você renuncie ao lambda.
— evanrmurphy

@evanrmurphy, Obrigado por notar isso. Eu fixei a resposta.
— Harish Shetty

@evanrmurphy você pode / deve revisar seu comentário de "Apenas Rails 3" para "Rails 3 e superior"?
— Kaichanvong

@kaichanvong Não estou familiarizado com Rails 4, então gostaria de dizer "Rails 3 (e superior?)", mas SO não me deixa editar o comentário: - /
— evanrmurphy

30

MySQL:

Model.all :condition => ["DATE(created_at) = ?", Date.today] # rails 2
Model.where("DATE(created_at) = ?", Date.today) # rails 3

PostgreSQL:

Model.all :condition => ["created_at::date = ?", Date.today] # rails 2
Model.where("created_at::date = ?", Date.today) # rails 3

19

Resposta de Mohit Jain adaptada para Rails3

Model.where "DATE(created_at) = DATE(?)", Time.now

16

O Rails 5.1 tem um all_dayhelper que é útil aqui.

Post.where(created_at: Date.today.all_day)

ou

Post.where(created_at: Date.parse("YYYY-MM-DD").all_day)

9

Post.where(created_at: Time.zone.now.beginning_of_day..Time.zone.now.end_of_day)

Isso "namescope" o atributo com o table_name.


5

model.rb

scope :posted_today, -> { posted_between_period(Time.now.midnight, Time.now.end_of_day) }

posts_controller.rb

Post.posted_today

2
@Pathiv, between_periodparece interessante. Não encontrei nenhuma documentação para isso. Você pode fornecer algum link? Como o Rails escolhe a coluna para comparação?
— Harish Shetty

1

Por alguma razão, nenhuma das outras soluções neste post nem em outras no StackOverflow funcionou para mim (usando Rails 4.2.4 e Ruby 2.2.3p173). Esta é a única consulta que consegui fazer com meu banco de dados Postgres:

Post.where("created_at >= TIMESTAMP 'now'")

-1

Para consultar os registros criados a partir de hoje

Use o escopo com arel

class Post < ActiveRecord::Base    
  scope :create_from_today, -> {
    where(arel_table[:created_at].gteq(Time.zone.now.beginning_of_day))
  }
end

Então podemos usá-lo

today_posts = Post.created_from_today

where('created_at >= now()')só encontraria itens onde created_at estivesse no futuro.
— PR Whitehead

Sim, eu o removeria da resposta, boa captura, obrigado
— Hieu Pham

O problema que você tem agora é que os registros marcados com datas futuras seriam apresentados, bem como os de hoje. Se você está tentando evitar o uso de entre, também deve especificar .lteq(Time.zone.now.end_of_day)).
— PR Whitehead

-4

No rails 4.2.3, para obter os registros criados hoje, usando o mysql use o seguinte.

@usergoals = Goal.where ("userid =: userid e Date (created_at) =: date", {userid: params [: id], date: Date.today})

aqui estou usando várias condições, se você quiser, pode editá-lo para uma única condição.

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.