MongoDB / Мангуст запрос на конкретную дату?
можно ли запросить конкретную дату ?
Я нашел в Поваренной книге монго, что мы можем сделать это для диапазона запрос диапазона дат Вот так:
db.posts.find({"created_on": {"$gte": start, "$lt": end}})
но возможно ли это на конкретную дату ? Это не работает :
db.posts.find({"created_on": new Date(2012, 7, 14) })
6 ответов:
Это должно работать, если даты, сохраненные в БД, не имеют времени (только год, месяц, день).
скорее всего, даты, которые вы сохранили были
new Date()
, которая включает в себя компоненты времени. Чтобы запросить эти времена, вам нужно создать диапазон дат, который включает все моменты в день.db.posts.find( //query today up to tonight {"created_on": {"$gte": new Date(2012, 7, 14), "$lt": new Date(2012, 7, 15)}})
для тех из нас, используя момент.js
var moment = require('moment') var today = moment().startOf('day') var tomorrow = moment(today).endOf('day') MyModel.find({ createdAt: { $gte: today.toDate(), $lt: tomorrow.toDate() } })
важно: все моменты изменчивы!
tomorrow = today.add(1, 'days')
не работает, так как он также мутируетtoday
. Звонюmoment(today)
решает эту проблему косвенно клонированияtoday
.
да, Объект даты дополняет дату и время, поэтому сравнение его только со значением даты не работает.
вы можете просто использовать $, где оператор для выражения более сложного условия с логическим выражением Javascript:)
db.posts.find({ '$where': 'this.created_on.toJSON().slice(0, 10) == "2012-07-14"' })
created_on
- это поле datetime и2012-07-14
- указанная дата.дата должна быть именно в ГГГГ-ММ-ДД.
Примечание: использовать
$where
экономно, это имеет последствия для производительности.
вы пробовали:
db.posts.find({"created_on": {"$gte": new Date(2012, 7, 14), "$lt": new Date(2012, 7, 15)}})
проблема, с которой вы столкнетесь, заключается в том, что даты хранятся как временные метки в Mongo. Итак, чтобы соответствовать дате, вы просите ее соответствовать метке времени. В вашем случае я думаю, что вы пытаетесь соответствовать дню (т. е. с 00:00 до 23:59 на конкретную дату). Если ваши даты хранятся без времени, то вы должны быть в порядке. В противном случае попробуйте указать дату как диапазон времени в тот же день (т. е. начало=00: 00, Конец=23: 59) если gte не делает работа.
вы можете использовать следующий подход для метода API, чтобы получить результаты с определенного дня:
# [HTTP GET] getMeals: (req, res) -> options = {} # eg. api/v1/meals?date=Tue+Jan+13+2015+00%3A00%3A00+GMT%2B0100+(CET) if req.query.date? date = new Date req.query.date date.setHours 0, 0, 0, 0 endDate = new Date date endDate.setHours 23, 59, 59, 59 options.date = $lt: endDate $gte: date Meal.find options, (err, meals) -> if err or not meals handleError err, meals, res else res.json createJSON meals, null, 'meals'
У нас была проблема, связанная с дублированными данными в нашей базе данных, с полем даты, имеющим несколько значений, где мы должны были иметь 1. Я думал, что добавлю, как мы решили проблему для справки.
у нас есть коллекция под названием "данные" с числовым полем "значение" и полем "дата". У нас был процесс, который мы считали идемпотентным, но в итоге добавляли 2 значения x в день при втором запуске:
{ "_id" : "1", "type":"x", "value":1.23, date : ISODate("2013-05-21T08:00:00Z")} { "_id" : "2", "type":"x", "value":1.23, date : ISODate("2013-05-21T17:00:00Z")}
нам нужен только 1 из 2 записей, поэтому пришлось прибегнуть javascript для очистки БД. Наш первоначальный подход состоял в том, чтобы повторить результаты и удалить любое поле со временем между 6 утра и 11 утра (все дубликаты были утром), но во время реализации внес изменения. Вот скрипт, используемый для его исправления:
var data = db.data.find({"type" : "x"}) var found = []; while (data.hasNext()){ var datum = data.next(); var rdate = datum.date; // instead of the next set of conditions, we could have just used rdate.getHour() and checked if it was in the morning, but this approach was slightly better... if (typeof found[rdate.getDate()+"-"+rdate.getMonth() + "-" + rdate.getFullYear()] !== "undefined") { if (datum.value != found[rdate.getDate()+"-"+rdate.getMonth() + "-" + rdate.getFullYear()]) { print("DISCREPENCY!!!: " + datum._id + " for date " + datum.date); } else { print("Removing " + datum._id); db.data.remove({ "_id": datum._id}); } } else { found[rdate.getDate()+"-"+rdate.getMonth() + "-" + rdate.getFullYear()] = datum.value; } }
а потом запустил его с
mongo thedatabase fixer_script.js