Я пишу заявку на Rails, але не можу знайти спосіб відносного часу, тобто, якщо задано певний часовий клас, він може обчислити "30 секунд тому" або "2 дні тому" або якщо це більше місяця "9/1/2008" тощо.
Я пишу заявку на Rails, але не можу знайти спосіб відносного часу, тобто, якщо задано певний часовий клас, він може обчислити "30 секунд тому" або "2 дні тому" або якщо це більше місяця "9/1/2008" тощо.
Відповіді:
Здається, ви шукаєте time_ago_in_words
метод (або distance_of_time_in_words
) від ActiveSupport. Назвіть це так:
<%= time_ago_in_words(timestamp) %>
ActiveSupport
, визначена в ActionView::Helpers::DateHelper
.
helper
який можна називати і отримувати доступ до цих методів. helper.time_ago_in_words(timestamp)
require 'active_support/core_ext'
Спочатку, а потім все готово до використання 7.days.ago
та інших подібних конструкцій.
Я написав це, але треба перевірити існуючі методи, щоб побачити, чи кращі вони.
module PrettyDate
def to_pretty
a = (Time.now-self).to_i
case a
when 0 then 'just now'
when 1 then 'a second ago'
when 2..59 then a.to_s+' seconds ago'
when 60..119 then 'a minute ago' #120 = 2 minutes
when 120..3540 then (a/60).to_i.to_s+' minutes ago'
when 3541..7100 then 'an hour ago' # 3600 = 1 hour
when 7101..82800 then ((a+99)/3600).to_i.to_s+' hours ago'
when 82801..172000 then 'a day ago' # 86400 = 1 day
when 172001..518400 then ((a+800)/(60*60*24)).to_i.to_s+' days ago'
when 518400..1036800 then 'a week ago'
else ((a+180000)/(60*60*24*7)).to_i.to_s+' weeks ago'
end
end
end
Time.send :include, PrettyDate
return
рядок у case
операторі під else
та видалити всі return
s.
+99
+800
+180000
?
Просто для уточнення рішення Ендрю Маршалла щодо використання time_ago_in_words
(для Rails 3.0 та Rails 4.0)
Якщо ви переглядаєте
<%= time_ago_in_words(Date.today - 1) %>
Якщо ви в контролері
include ActionView::Helpers::DateHelper
def index
@sexy_date = time_ago_in_words(Date.today - 1)
end
Контролери не мають модуля ActionView :: Helpers :: DateHelper, який імпортується за замовчуванням.
Примітка. Не імпортувати помічників у свої контролери - це не "рейковий шлях". Помічники допомагають переглядати. Метод time_ago_in_words було вирішено стати об'єктом перегляду в тріаді MVC . (Я не згоден, але коли в Римі ...)
Ви можете використовувати арифметичні оператори для відносного часу.
Time.now - 2.days
Подарую вам 2 дні тому.
2.days.since
або2.days.from_now
Щось подібне спрацювало б.
def relative_time(start_time)
diff_seconds = Time.now - start_time
case diff_seconds
when 0 .. 59
puts "#{diff_seconds} seconds ago"
when 60 .. (3600-1)
puts "#{diff_seconds/60} minutes ago"
when 3600 .. (3600*24-1)
puts "#{diff_seconds/3600} hours ago"
when (3600*24) .. (3600*24*30)
puts "#{diff_seconds/(3600*24)} days ago"
else
puts start_time.strftime("%m/%d/%Y")
end
end
#{diff_seconds/360}
повинно бути #{diff_seconds/3600}
. Я це відредагував.
Оскільки найбільш відповідь тут пропонує time_ago_in_words .
Замість використання:
<%= time_ago_in_words(comment.created_at) %>
У Рейлах віддайте перевагу:
<abbr class="timeago" title="<%= comment.created_at.getutc.iso8601 %>">
<%= comment.created_at.to_s %>
</abbr>
разом із бібліотекою jQuery http://timeago.yarp.com/ з кодом:
$("abbr.timeago").timeago();
Основна перевага: кешування
http://rails-bestpractices.com/posts/2012/02/10/not-use-time_ago_in_words/
time_ago_in_words
не час S
Погляньте на методи екземпляра тут:
Тут є корисні методи, такі як вчора, завтра, begin_of_week, назад тощо.
Приклади:
Time.now.yesterday
Time.now.ago(2.days).end_of_day
Time.now.next_month.beginning_of_month
Я написав самоцвіт, який робить це для об'єктів Rails ActiveRecord. У прикладі використовується create_at, але він також працюватиме оновлений_at або що-небудь з класом ActiveSupport :: TimeWithZone.
Просто встановіть дорогоцінний камінь і зателефонуйте на метод «досить» у вашому екземплярі TimeWithZone.
Якщо ви створюєте додаток Rails, вам слід скористатися
Time.zone.now
Time.zone.today
Time.zone.yesterday
Це дає вам час або дату в часовому поясі, з яким ви налаштували свою програму Rails.
Наприклад, якщо ви налаштуєте свою програму на використання UTC, вона Time.zone.now
завжди буде в часі UTC (на зміну Британського літнього часу, наприклад, це не вплине).
Розрахувати відносний час досить просто, наприклад
Time.zone.now - 10.minute
Time.zone.today.days_ago(5)
Інший підхід полягає в тому, щоб вивантажити деяку логіку з бекенда і змусити браузера виконувати цю роботу за допомогою плагінів Javascript, таких як:
jQuery час тому або його адаптація Rails Gem