Как удалить данные более чем 1 недели назад в MongoDB?

#mongodb

Вопрос:

Я создал веб-скребок для хранения данных в течение недели, чтобы найти тенденцию. Я написал код для удаления данных более недели назад при каждом запуске скрипта. Однако данные все еще хранятся более недели назад, есть ли для этого причина?»

пример данных монеты, созданных в поле, выглядит следующим образом

     "createdAt": {
    "$date": "2021-08-11T10:55:19.843Z"
},

coinSchema.statics.deleteOldData = async function () {
  // delete old data
  const today = new Date(Date.now());
  today.setHours(0, 0, 0, 0);
  const oneWeekAgo = new Date(Date.now());
  const pastDate = oneWeekAgo.getDate() - 7;
  oneWeekAgo.setDate(pastDate);

  await this.deleteMany({
    createdAt: {
      $gte: today,
    }, // 16 < 17 wont delete it prevent duplicates for one day
  });
  await this.deleteMany({
    createdAt: {
      $lt: pastDate,
    }, // from 1 week ago
  });
};
 

в сценарии у меня есть этот запуск

 async function main() {
await Coin.deleteOldData();
 

моя модель монеты выглядит так :

     const coinSchema = mongoose.Schema(
  {
    specNo: {
      type: String,
      required: true,
    },
    coinName: {
      type: String,
      required: true,
    },
    fullName: {
      type: String,
      required: false,
    },
    category: {
      type: String,
    },
    array: [
      {
        GradeName: String,
        PopulationCount: String,
        trend: { type: Number, default: 0 },
      },
    ],
  },
  {
    timestamps: true,
  }
);
 

Комментарии:

1. Как выглядят ваши данные сбора? Возможно, вы храните значения дат в виде строки (что является недостатком дизайна) вместо правильных Date объектов.

2. При работе с датами я рекомендую использовать moment.js библиотека . Было бы createdAt: { $lt: moment().startOf('day').subtract(7, 'day').toDate() } и createdAt: { $gte: moment().startOf('day').toDate() }

3. «Дата создания»: { «дата$»: «2021-08-11T10:55:19.843 Z» },

Ответ №1:

Вы смотрели на индекс на основе TTL? https://docs.mongodb.com/manual/core/index-ttl/

Это хороший способ очистки старых данных, когда об этом заботится сама БД. В вашем случае 7 дней-это 604800 секунд, поэтому, если вы создадите индекс на createdAt с ttl 604800, то у вас все должно быть хорошо!

 db.collection.createIndex( { "createdAt ": 1 }, { expireAfterSeconds: 604800 } )
 

Комментарии:

1. Должен ли я включить это в модель? или в моем веб-скребке?

2. этот индекс создается на сервере БД. обычно администратор базы данных создавал индексы. Кроме того, это одноразовая настройка. как только вы настроите индекс на основе TTL, все готово!

Ответ №2:

Ты можешь сделать это вот так:

 db.collection.deleteMany({
  createdAt: { $lte: new Date(Date.now() - 7 * 24 * 60 * 60 * 1000).toISOString() },
})