Хранить массив переменной длины в mongodb с помощью mongoose

Я использую форму на стороне клиента, где пользователь может загружать файлы столько, сколько он хочет, а затем я отправляю все это с помощью axios.

Получая его в NodeJS, я использую Multer для получения файлов и их информации с помощью req.files, например:

[ { fieldname: 'file1',
    originalname: 'someimage.jpg',
    encoding: '7bit',
    mimetype: 'image/jpeg',
    destination: './uploads/',
    filename: '71027041755f49366c132555066d5b89',
    path: 'uploads\\71027041755f49366c132555066d5b89',
    size: 69336 } ]

Как мы видим, это массив, который может содержать более одного файла, что неплохо, но здесь возникает моя проблема.

Я хочу сохранить информацию об этих файлах в MongoDB с помощью Mongoose, чтобы я знал, как вызывается файл, его место назначения, размер и т. д.

Я определил схему в Mongoose следующим образом:

const someSchema = new Schema({
  files: {
    originalname: String,
    filename: String,
    mimetype: String,
    size: String,
    destination: String,
    path: String
  }
});

Но это позволило бы мне хранить информацию только об одном файле. Я также пробовал ранее:

const someSchema = new Schema({
  files: Array
});

Но это не сработает (TypeError: Cannot set property 'originalname' of undefined). Я также пробовал установить Object, который тоже выдает ошибки (TypeError: Cannot read property '0' of undefined).

Кстати, читаю "файлы" с:

 for (let i = 0; i < req.files.length; i++) {
      someschema.files[i].originalname = req.files[i].originalname;
      someschema.files[i].filename = req.files[i].filename;
      someschema.files[i].mimetype = req.files[i].mimetype;
      someschema.files[i].size = req.files[i].size;
      someschema.files[i].destination = req.files[i].destination;
      someschema.files[i].path = req.files[i].path;
    }

Регистрируя каждый приведенный выше req.files[i].XXX, все определяется как надо.

Есть ли способ создать схему, которая принимает несколько «файлов»?

Другими словами: есть ли способ создать схему, которая принимает массив с несколькими объектами, если возможно, с этими точными ключами?

Заранее спасибо.

Обновлено: Я придумал files: [Object], но это тоже не сработает (TypeError).

0
0
411
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Используйте $addToSet, чтобы поместить другой объект в массив.

Вы можете использовать $push вместо $addToSet, но это позволит вам вставить повторяющийся объект.

Схема:

var UserSchema = new Schema({
  files: [{
    originalname: String,
    filename: String,
    mimetype: String,
    size: String,
    destination: String,
    path: String
  }]
});

Чтобы вставить другой объект в массив.

let obj = {
  originalname: "11",
  filename: "11",
  mimetype: "11",
  size: "11",
  destination: "11",
  path: "11"
}

User.update({
  _id: mongoose.Types.ObjectId("5bd99f95f255307d51f32578")
}, {
    $addToSet: { files: obj}
}).exec(function(err, updated){
  console.log(updated);
})

======== Обновление =======

Ваш someschema.files имеет самую низкую длину. Например, для 2, и вы повторяете больше, чем это, с индексом i. Попробуйте ниже:

for (let i = 0; i < req.files.length; i++) {
  let obj = {};
  obj.originalname = req.files[i].originalname;
  obj.filename = req.files[i].filename;
  obj.mimetype = req.files[i].mimetype;
  obj.size = req.files[i].size;
  obj.destination = req.files[i].destination;
  obj.path = req.files[i].path;

  someschema.files.push(obj); // lastly push whole object.
}

Хранение его с req.files[i] эта схема также дает TypeError: Cannot set property 'originalname' of undefined. Я считаю, что моя ошибка записывает его с помощью [i] в ​​массив, но как это сделать?

Fusseldieb 31.10.2018 13:36

Это потому, что у вашего someschema.files самая низкая длина. Например, 2, и вы повторяете больше, чем это, с индексом

Hardik Shah 31.10.2018 13:41

Это сработало. Большое тебе спасибо. Также спасибо за ваше объяснение, почему это не сработало раньше.

Fusseldieb 31.10.2018 13:57

@Fusseldieb, мое удовольствие.

Hardik Shah 31.10.2018 14:00

Попробуйте заключить свои поля внутрь []

const someSchema = new Schema({
  files: [{
    originalname: String,
    filename: String,
    mimetype: String,
    size: String,
    destination: String,
    path: String
  }]
});

Спасибо за ваш ответ, но это в основном то, что предлагал и другой ответ.

Fusseldieb 31.10.2018 13:59

Другие вопросы по теме