CouchDB / Cradle Как добавить изображения? - PullRequest
1 голос
/ 27 апреля 2011

Итак, в основном я хочу предоставить пользователю возможность загружать изображения при регистрации. Я понятия не имею, с чего начать всегда. Я знаю, что CouchDB поддерживает вложения, но как именно это работает с Cradle.

Я нашел следующий код в документации Cradle

saveAttachment: function (/* id, [rev], attachmentName, contentType, dataOrStream */) {

Так что я знаю, что это может сохранить вложения. Как бы я передал изображение тогда? Я предполагаю, что в HTML, я должен использовать

form(action='/upload', enctype='multipart/form-data', method='post')
input(type='file', name='upload')
input(type='submit', value='Upload')

Но куда мне идти оттуда? Не будет ли этот шаг сохранить изображение где-нибудь на сервере. Затем мне нужно как-то получить адрес изображения и передать его в колыбель, чтобы сохранить его как вложение в базе данных CouchDB.

Заранее спасибо, если вы можете мне помочь!

Ответы [ 3 ]

2 голосов
/ 22 мая 2011

Вам нужно взять входящий поток из формы и затем отправить поток в CouchDB через Cradle .

Отправка потока в Cradle, вероятно, самый простой бит.В этом примере показано, как сделать это с локальным файлом:

db.saveAttachment( 
    doc.id, 
    doc.rev, 
    attachmentId,
    mimetype, 
    fs.createReadStream(path),
    function( err, data ){
        console.log(data);
    }
);

Более сложным, на мой взгляд, является управление входящими файлами.Они поступают в виде составного потока, а не сохраняются в файл.Я предпочел бы передать этот код на грозный , прямо или косвенно, через connect-form , если вы используете Connect или Express.

Мое текущее соединение-форм код может быть сведен к следующему:

req.form.complete(function(err, fields, files){
    if ( err ) // handle err
    else
    {
        db.saveAttachment( 
            doc.id, 
            doc.rev, 
            attachmentId,
            mimetype, 
            fs.createReadStream(files.name),
            function( err, data ){
                console.log(data);
            }
        );
    }
});

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

Другой пакет, о котором вам следует знать, если вы имеете дело с загрузкой изображений, это node-imagemagick, , который, как вы можете ожидать из названия, является узломОболочка .js для ImageMagick.

1 голос
/ 20 марта 2013

Я написал некоторую документацию по вложениям, которая, как мы надеемся, скоро будет добавлена ​​в readme базовой станции.Пока что здесь есть соответствующий раздел

Вложения

Cradle поддерживает запись, чтение и удаление вложений.Операции чтения и записи могут быть буферизованными или потоковыми

Запись

Вы можете буферизовать все тело вложения и отправить все сразу как один запрос.Функция обратного вызова сработает после завершения загрузки вложения или возникновения ошибки

Синтаксис

db.saveAttachment(idData, attachmentData, callbackFunction)

Пример Скажем, вы хотите сохранитьтекстовый документ в виде вложения с именем «fooAttachment.txt» и содержимым «текст документа Foo»

var doc = <some existing document>
var id = doc._id
var rev = doc._rev
var idAndRevData = {
  id: id,
  rev: rev
}
var attachmentData = {
  name: 'fooAttachment.txt',
  'Content-Type': 'text/plain',
  body: 'Foo document text'
}
db.saveAttachment(idAndRevData, attachmentData, function (err, reply) {
  if (err) {
    console.dir(err)
    return
  }
  console.dir(reply)
})

Streaming

Вы можете использовать поток чтения для загрузки тела вложения, а несначала буферизируем все телоФункция обратного вызова сработает после завершения потоковой загрузки или возникновения ошибки

Синтаксис

var doc = savedDoc // <some saved couchdb document which has an attachment>
var id = doc._id
var rev = doc._rev
var idAndRevData = {
  id: id,
  rev: rev
}
var attachmentData = {
  name: attachmentName               // something like 'foo.txt'
  'Content-Type': attachmentMimeType // something like 'text/plain', 'application/pdf', etc.
  body: rawAttachmentBody            // something like 'foo document body text'
}
var readStream = fs.createReadStream('/path/to/file/')
var writeStream  = db.saveAttachment(idData, attachmentData, callbackFunction)
readStream.pipe(writeStream)

Когда потоковая загрузка будет завершена, функция обратного вызова сработает

Пример Присоедините файл PDF с именем 'bar.pdf', расположенный по пути './data/bar.pdf' к существующему документу

var path = require('path')
var fs = require('fs')
// this document should already be saved in the couchdb database
var doc = {
  _id: 'fooDocumentID',
  _rev: 'fooDocumentRev'
}
var idData = {
  id: doc._id,
  rev: doc._rev
}
var filename = 'bar.pdf' // this is the filename that will be used in couchdb. It can be different from your source filename if desired
var filePath = path.join(__dirname, 'data', 'bar.pdf')
var readStream = fs.createReadStream
// note that there is no body field here since we are streaming the upload
var attachmentData = {
  name: 'fooAttachment.txt',
  'Content-Type': 'text/plain'
}
db.saveAttachment(idData, attachmentData, function (err, reply) {
  if (err) {
    console.dir(err)
    return
  }
  console.dir(reply)
}, readStream)

Чтение

Буферизуемый

Вы можете буферизовать все вложение и получить все сразу.Функция обратного вызова сработает после завершения загрузки или возникновения ошибки.Вторым параметром в обратном вызове будут двоичные данные вложения

Синтаксис

db.getAttachment(documentID, attachmentName, callbackFunction)

Пример Скажем, вы хотите прочитать обратновложение, которое было сохранено с именем 'foo.txt'

var doc = <some saved document that has an attachment with name *foo.txt*>
var id = doc._id
var attachmentName = 'foo.txt'
db.getAttachment(id, attachmentName, function (err, reply) {
  if (err) {
    console.dir(err)
    return
  }
  console.dir(reply)
})

Streaming

Вы также можете транслировать вложение.Если вложение является большим, может быть полезно потоковое воспроизведение, чтобы ограничить потребление памятиФункция обратного вызова сработает после завершения потока загрузки.Обратите внимание, что в функцию обратного вызова передается только один параметр ошибки.Ошибка равна нулю, ошибки не возникли или объект ошибки, если произошла ошибка при загрузке вложения.Нет второго параметра, содержащего данные вложения, как в буферизованном примере чтения

Синтаксис

var readStream = db.getAttachment(documentID, attachmentName, callbackFunction)

Пример Скажем, вы хотите прочитать обратновложение, которое было сохранено с именем 'foo.txt'.Однако вложение foo.txt очень большое, поэтому вы хотите передавать его на диск, а не буферизовать весь файл в памяти

var doc = <some saved document that has an attachment with name *foo.txt*>
var id = doc._id
var attachmentName = 'foo.txt'
var downloadPath = path.join(__dirname, 'foo_download.txt')
var writeStream = fs.createWriteStream(downloadPath)
var readStream = db.getAttachment('piped-attachment', 'foo.txt', function (err) { // note no second reply paramter
  if (err) {
    console.dir(err)
    return
  }
  console.dir('download completed and written to file on disk at path', downloadPath)
})
readStream.pipe(writeStream)

Удаление

Вы можете удалить загруженные вложения с помощью _id иимя вложения

синтаксис

db.removeAttachment(documentID, attachmentName, callbackFunction)

Пример Допустим, вы хотите удалить вложение, которое было сохранено с именем 'foo.txt'

var doc = <some saved document that has an attachment with name *foo.txt*>
var id = doc._id
var attachmentName = 'foo.txt'
db.removeAttachment(id, attachmentName, function (err, reply) {
  if (err) {
    console.dir(err)
    return
  }
  console.dir(reply)
})
1 голос
/ 06 марта 2013

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

...