{"id":816,"date":"2012-01-19T19:42:00","date_gmt":"2012-01-19T19:42:00","guid":{"rendered":"http:\/\/www.javacodegeeks.com\/2012\/10\/streaming-files-from-mongodb-gridfs.html"},"modified":"2012-10-21T22:43:31","modified_gmt":"2012-10-21T22:43:31","slug":"streaming-files-from-mongodb-gridfs","status":"publish","type":"post","link":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html","title":{"rendered":"Streaming Files from MongoDB GridFS"},"content":{"rendered":"<div dir=\"ltr\" style=\"text-align: left\">Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from <a href=\"http:\/\/www.mongodb.org\/display\/DOCS\/GridFS\">MongoDB GridFS<\/a> for downloads (rather than pulling the whole file into memory and then serving it up). I promised to blog about this but unfortunately my specific usage was a little coupled to the domain on my project so I couldn\u2019t just show it off as is. So I\u2019ve put together an <a href=\"https:\/\/github.com\/jamescarr\/nodejs-mongodb-streaming\">example node.js+GridFS application<\/a> and shared it on github and will use this post to explain how I accomplished it. <img decoding=\"async\" alt=\":)\" class=\"wp-smiley\" src=\"http:\/\/blog.james-carr.org\/wp-includes\/images\/smilies\/icon_smile.gif\" \/><\/p>\n<p><span class=\"Apple-style-span\" style=\"font-size: large\">GridFS module<\/span><\/p>\n<p>First off, special props go to <a href=\"https:\/\/twitter.com\/#!\/tjholowaychuk\">tjholowaychuk<\/a> who responded in the #node.js irc channel when I asked if anyone has had luck with using GridFS from <a href=\"http:\/\/mongoosejs.com\/\">mongoose<\/a>. A lot of my resulting code is derived from an gist he shared with me. Anyway, to the code. I\u2019ll describe how I\u2019m using gridfs and after setting the ground work illustrate how simple it is to stream files from GridFS.<\/p>\n<p>I created a gridfs module that basically accesses GridStore through mongoose (which I use throughout my application) that can also share the db connection created when connecting mongoose to the mongodb server.<\/p>\n<pre class=\"brush: java;\">mongoose = require \"mongoose\"\r\nrequest  = require \"request\"\r\n\r\nGridStore = mongoose.mongo.GridStore\r\nGrid      = mongoose.mongo.Grid\r\nObjectID = mongoose.mongo.BSONPure.ObjectID\r\n<\/pre>\n<p>We can\u2019t get files from mongodb if we cannot put anything into it, so let\u2019s create a putFile operation.<\/p>\n<pre class=\"brush: java;\">exports.putFile = (path, name, options..., fn) -&gt;\r\n  db = mongoose.connection.db\r\n  options = parse(options)\r\n  options.metadata.filename = name\r\n  new GridStore(db, name, \"w\", options).open (err, file) -&gt;\r\n    return fn(err)  if err\r\n    file.writeFile path, fn\r\n\r\n\r\n\r\nparse = (options) -&gt;\r\n  opts = {}\r\n  if options.length &gt; 0\r\n    opts = options[0]\r\n  if !opts.metadata\r\n    opts.metadata = {}\r\n  opts\r\n<\/pre>\n<p>This really just delegates to the putFile operation that exists in GridStore as part of the mongodb module. I also have a little logic in place to parse options, providing defaults if none were provided. One interesting feature to note is that I store the filename in the metadata because at the time I ran into a funny issue where files retrieved from gridFS had the id as the filename (even though a look in mongo reveals that the filename is in fact in the database).<div style=\"display:inline-block; margin: 15px 0;\"> <div id=\"adngin-JavaCodeGeeks_incontent_video-0\" style=\"display:inline-block;\"><\/div> <\/div><\/p>\n<p>Now the get operation. The original implementation of this simply passed the contents as a buffer to the provided callback by calling store.readBuffer(), but this is now changed to pass the resulting store object to the callback. The value in this is that the caller can use the store object to access metadata, contentType, and other details. The user can also determine how they want to read the file (either into memory or using a ReadableStream).<\/p>\n<pre class=\"brush: java;\">exports.get = (id, fn) -&gt;\r\n  db = mongoose.connection.db\r\n  id = new ObjectID(id)\r\n  store = new GridStore(db, id, \"r\",\r\n    root: \"fs\"\r\n  )\r\n  store.open (err, store) -&gt;\r\n    return fn(err)  if err\r\n    # band-aid\r\n    if \"#{store.filename}\" == \"#{store.fileId}\" and store.metadata and store.metadata.filename\r\n      store.filename = store.metadata.filename\r\n    fn null, store\r\n<\/pre>\n<p>This code just has a small blight in that it checks to see if the filename and fileId are equal. If they are, it then checks to see if metadata.filename is set and sets store.filename to the value found there. I\u2019ve tabled the issue to investigate further later. <img decoding=\"async\" alt=\":)\" class=\"wp-smiley\" src=\"http:\/\/blog.james-carr.org\/wp-includes\/images\/smilies\/icon_smile.gif\" \/><\/p>\n<p><span class=\"Apple-style-span\" style=\"font-size: large\">The Model<\/span><\/p>\n<p>In my specific instance, I wanted to attach files to a model. In this example, let\u2019s pretend that we have an Application for something (job, a loan application, etc) that we can attach any number of files to. Think of tax receipts, a completed application, other scanned documents.<\/p>\n<pre class=\"brush: java;\">ApplicationSchema = new mongoose.Schema(\r\n  name: String\r\n  files: [ mongoose.Schema.Mixed ]\r\n)\r\nApplicationSchema.methods.addFile = (file, options, fn) -&gt;\r\n  gridfs.putFile file.path, file.filename, options, (err, result) =&gt;\r\n    @files.push result\r\n    @save fn\r\n<\/pre>\n<p>Here I define files as an array of Mixed object types (meaning they can be anything) and a method addFile which basically takes an object that at least contains a path and filename attribute. It uses this to save the file to gridfs and stores the resulting gridstore file object in the files array (this contains stuff like an id, uploadDate, contentType, name, size, etc).<\/p>\n<p><span class=\"Apple-style-span\" style=\"font-size: large\">Handling Requests<\/span><\/p>\n<p>This all plugs in to the request handler to handle form submissions to \/new. All this entails is creating an Application model instance, adding the uploaded file from the request (in this case we named the file field \u201cfile\u201d,<span class=\"Apple-style-span\" style=\"font-family: 'Courier New', Courier, monospace\"> hence req.files.file<\/span>) and saving it.<\/p>\n<pre class=\"brush: java;\">app.post \"\/new\", (req, res) -&gt;\r\n  application = new Application()\r\n  application.name = req.body.name\r\n  opts = \r\n    content_type: req.files.file.type\r\n  application.addFile req.files.file, opts, (err, result) -&gt;\r\n    res.redirect \"\/\"\r\n<\/pre>\n<p>Now the sum of all this work allows us to reap the rewards by making it super simple to download a requested file from gridFS.<\/p>\n<pre class=\"brush: java;\">app.get \"\/file\/:id\", (req, res) -&gt;\r\n  gridfs.get req.params.id, (err, file) -&gt;\r\n    res.header \"Content-Type\", file.type\r\n    res.header \"Content-Disposition\", \"attachment; filename=#{file.filename}\"\r\n    file.stream(true).pipe(res)\r\n<\/pre>\n<p>Here we simply look up a file by id and use the resulting file object to set Content-Type and Content-Disposition fields and finally make use of <span class=\"Apple-style-span\" style=\"font-family: 'Courier New', Courier, monospace\">ReadableStream::pipe<\/span> to write the file out to the response object (which is an instance of WritableStream). This is the piece of magic that streams data from MongoDB to the client side.<\/p>\n<p><span class=\"Apple-style-span\" style=\"font-size: large\">Ideas<\/span><\/p>\n<p>This is just a humble beginning. Other ideas include completely encapsulating gridfs within the model. Taking things further we could even turn the gridfs model into a mongoose plugin to allow completely blackboxed usage of gridfs.<\/p>\n<p>Feel free to check the <a href=\"https:\/\/github.com\/jamescarr\/nodejs-mongodb-streaming\">project <\/a>out and let me know if you have ideas to take it even further. Fork away! <img decoding=\"async\" alt=\":)\" class=\"wp-smiley\" src=\"http:\/\/blog.james-carr.org\/wp-includes\/images\/smilies\/icon_smile.gif\" \/><\/p>\n<p><strong><i>Reference: <\/i><\/strong><a href=\"http:\/\/blog.james-carr.org\/2012\/01\/09\/streaming-files-from-mongodb-gridfs\/\">Streaming Files from MongoDB GridFS<\/a>&nbsp;from our <a href=\"http:\/\/www.javacodegeeks.com\/p\/jcg.html\">JCG partner<\/a>&nbsp;James Carr at the&nbsp;<a href=\"http:\/\/blog.james-carr.org\/\">Rants and Musings of an Agile Developer<\/a>&nbsp;blog<\/p>\n<\/div>\n","protected":false},"excerpt":{"rendered":"<p>Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling the whole file into memory and then serving it up). I promised to blog about this but unfortunately my specific usage was a little coupled to the domain &hellip;<\/p>\n","protected":false},"author":19,"featured_media":187,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[8],"tags":[112,113],"class_list":["post-816","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-enterprise-java","tag-mongodb","tag-nosql"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.5 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>Streaming Files from MongoDB GridFS - Java Code Geeks<\/title>\n<meta name=\"description\" content=\"Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Streaming Files from MongoDB GridFS - Java Code Geeks\" \/>\n<meta property=\"og:description\" content=\"Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling\" \/>\n<meta property=\"og:url\" content=\"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html\" \/>\n<meta property=\"og:site_name\" content=\"Java Code Geeks\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/javacodegeeks\" \/>\n<meta property=\"article:published_time\" content=\"2012-01-19T19:42:00+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2012-10-21T22:43:31+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2012\/10\/mongodb-logo.jpg\" \/>\n\t<meta property=\"og:image:width\" content=\"150\" \/>\n\t<meta property=\"og:image:height\" content=\"150\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/jpeg\" \/>\n<meta name=\"author\" content=\"James Carr\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@javacodegeeks\" \/>\n<meta name=\"twitter:site\" content=\"@javacodegeeks\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"James Carr\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"5 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html\"},\"author\":{\"name\":\"James Carr\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#\\\/schema\\\/person\\\/7558615091dc8194304741268f9a90f9\"},\"headline\":\"Streaming Files from MongoDB GridFS\",\"datePublished\":\"2012-01-19T19:42:00+00:00\",\"dateModified\":\"2012-10-21T22:43:31+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html\"},\"wordCount\":772,\"commentCount\":1,\"publisher\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#organization\"},\"image\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#primaryimage\"},\"thumbnailUrl\":\"https:\\\/\\\/www.javacodegeeks.com\\\/wp-content\\\/uploads\\\/2012\\\/10\\\/mongodb-logo.jpg\",\"keywords\":[\"MongoDB\",\"NoSQL\"],\"articleSection\":[\"Enterprise Java\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html\",\"url\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html\",\"name\":\"Streaming Files from MongoDB GridFS - Java Code Geeks\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#primaryimage\"},\"image\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#primaryimage\"},\"thumbnailUrl\":\"https:\\\/\\\/www.javacodegeeks.com\\\/wp-content\\\/uploads\\\/2012\\\/10\\\/mongodb-logo.jpg\",\"datePublished\":\"2012-01-19T19:42:00+00:00\",\"dateModified\":\"2012-10-21T22:43:31+00:00\",\"description\":\"Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#primaryimage\",\"url\":\"https:\\\/\\\/www.javacodegeeks.com\\\/wp-content\\\/uploads\\\/2012\\\/10\\\/mongodb-logo.jpg\",\"contentUrl\":\"https:\\\/\\\/www.javacodegeeks.com\\\/wp-content\\\/uploads\\\/2012\\\/10\\\/mongodb-logo.jpg\",\"width\":150,\"height\":150},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/2012\\\/01\\\/streaming-files-from-mongodb-gridfs.html#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/www.javacodegeeks.com\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Java\",\"item\":\"https:\\\/\\\/www.javacodegeeks.com\\\/category\\\/java\"},{\"@type\":\"ListItem\",\"position\":3,\"name\":\"Enterprise Java\",\"item\":\"https:\\\/\\\/www.javacodegeeks.com\\\/category\\\/java\\\/enterprise-java\"},{\"@type\":\"ListItem\",\"position\":4,\"name\":\"Streaming Files from MongoDB GridFS\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#website\",\"url\":\"https:\\\/\\\/www.javacodegeeks.com\\\/\",\"name\":\"Java Code Geeks\",\"description\":\"Java Developers Resource Center\",\"publisher\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#organization\"},\"alternateName\":\"JCG\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/www.javacodegeeks.com\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#organization\",\"name\":\"Exelixis Media P.C.\",\"url\":\"https:\\\/\\\/www.javacodegeeks.com\\\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#\\\/schema\\\/logo\\\/image\\\/\",\"url\":\"https:\\\/\\\/www.javacodegeeks.com\\\/wp-content\\\/uploads\\\/2022\\\/06\\\/exelixis-logo.png\",\"contentUrl\":\"https:\\\/\\\/www.javacodegeeks.com\\\/wp-content\\\/uploads\\\/2022\\\/06\\\/exelixis-logo.png\",\"width\":864,\"height\":246,\"caption\":\"Exelixis Media P.C.\"},\"image\":{\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#\\\/schema\\\/logo\\\/image\\\/\"},\"sameAs\":[\"https:\\\/\\\/www.facebook.com\\\/javacodegeeks\",\"https:\\\/\\\/x.com\\\/javacodegeeks\"]},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/www.javacodegeeks.com\\\/#\\\/schema\\\/person\\\/7558615091dc8194304741268f9a90f9\",\"name\":\"James Carr\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/751c55f22a64fa5ac630c3bddaf1a4f4e11c442aaa9fc308004564cdca64b900?s=96&d=mm&r=g\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/751c55f22a64fa5ac630c3bddaf1a4f4e11c442aaa9fc308004564cdca64b900?s=96&d=mm&r=g\",\"contentUrl\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/751c55f22a64fa5ac630c3bddaf1a4f4e11c442aaa9fc308004564cdca64b900?s=96&d=mm&r=g\",\"caption\":\"James Carr\"},\"sameAs\":[\"http:\\\/\\\/blog.james-carr.org\\\/\"],\"url\":\"https:\\\/\\\/www.javacodegeeks.com\\\/author\\\/James-Carr\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"Streaming Files from MongoDB GridFS - Java Code Geeks","description":"Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html","og_locale":"en_US","og_type":"article","og_title":"Streaming Files from MongoDB GridFS - Java Code Geeks","og_description":"Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling","og_url":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html","og_site_name":"Java Code Geeks","article_publisher":"https:\/\/www.facebook.com\/javacodegeeks","article_published_time":"2012-01-19T19:42:00+00:00","article_modified_time":"2012-10-21T22:43:31+00:00","og_image":[{"width":150,"height":150,"url":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2012\/10\/mongodb-logo.jpg","type":"image\/jpeg"}],"author":"James Carr","twitter_card":"summary_large_image","twitter_creator":"@javacodegeeks","twitter_site":"@javacodegeeks","twitter_misc":{"Written by":"James Carr","Est. reading time":"5 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#article","isPartOf":{"@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html"},"author":{"name":"James Carr","@id":"https:\/\/www.javacodegeeks.com\/#\/schema\/person\/7558615091dc8194304741268f9a90f9"},"headline":"Streaming Files from MongoDB GridFS","datePublished":"2012-01-19T19:42:00+00:00","dateModified":"2012-10-21T22:43:31+00:00","mainEntityOfPage":{"@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html"},"wordCount":772,"commentCount":1,"publisher":{"@id":"https:\/\/www.javacodegeeks.com\/#organization"},"image":{"@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#primaryimage"},"thumbnailUrl":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2012\/10\/mongodb-logo.jpg","keywords":["MongoDB","NoSQL"],"articleSection":["Enterprise Java"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#respond"]}]},{"@type":"WebPage","@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html","url":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html","name":"Streaming Files from MongoDB GridFS - Java Code Geeks","isPartOf":{"@id":"https:\/\/www.javacodegeeks.com\/#website"},"primaryImageOfPage":{"@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#primaryimage"},"image":{"@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#primaryimage"},"thumbnailUrl":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2012\/10\/mongodb-logo.jpg","datePublished":"2012-01-19T19:42:00+00:00","dateModified":"2012-10-21T22:43:31+00:00","description":"Not too long ago I tweeted what I felt was a small triumph on my latest project, streaming files from MongoDB GridFS for downloads (rather than pulling","breadcrumb":{"@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html"]}]},{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#primaryimage","url":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2012\/10\/mongodb-logo.jpg","contentUrl":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2012\/10\/mongodb-logo.jpg","width":150,"height":150},{"@type":"BreadcrumbList","@id":"https:\/\/www.javacodegeeks.com\/2012\/01\/streaming-files-from-mongodb-gridfs.html#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/www.javacodegeeks.com\/"},{"@type":"ListItem","position":2,"name":"Java","item":"https:\/\/www.javacodegeeks.com\/category\/java"},{"@type":"ListItem","position":3,"name":"Enterprise Java","item":"https:\/\/www.javacodegeeks.com\/category\/java\/enterprise-java"},{"@type":"ListItem","position":4,"name":"Streaming Files from MongoDB GridFS"}]},{"@type":"WebSite","@id":"https:\/\/www.javacodegeeks.com\/#website","url":"https:\/\/www.javacodegeeks.com\/","name":"Java Code Geeks","description":"Java Developers Resource Center","publisher":{"@id":"https:\/\/www.javacodegeeks.com\/#organization"},"alternateName":"JCG","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.javacodegeeks.com\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/www.javacodegeeks.com\/#organization","name":"Exelixis Media P.C.","url":"https:\/\/www.javacodegeeks.com\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/www.javacodegeeks.com\/#\/schema\/logo\/image\/","url":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2022\/06\/exelixis-logo.png","contentUrl":"https:\/\/www.javacodegeeks.com\/wp-content\/uploads\/2022\/06\/exelixis-logo.png","width":864,"height":246,"caption":"Exelixis Media P.C."},"image":{"@id":"https:\/\/www.javacodegeeks.com\/#\/schema\/logo\/image\/"},"sameAs":["https:\/\/www.facebook.com\/javacodegeeks","https:\/\/x.com\/javacodegeeks"]},{"@type":"Person","@id":"https:\/\/www.javacodegeeks.com\/#\/schema\/person\/7558615091dc8194304741268f9a90f9","name":"James Carr","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/secure.gravatar.com\/avatar\/751c55f22a64fa5ac630c3bddaf1a4f4e11c442aaa9fc308004564cdca64b900?s=96&d=mm&r=g","url":"https:\/\/secure.gravatar.com\/avatar\/751c55f22a64fa5ac630c3bddaf1a4f4e11c442aaa9fc308004564cdca64b900?s=96&d=mm&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/751c55f22a64fa5ac630c3bddaf1a4f4e11c442aaa9fc308004564cdca64b900?s=96&d=mm&r=g","caption":"James Carr"},"sameAs":["http:\/\/blog.james-carr.org\/"],"url":"https:\/\/www.javacodegeeks.com\/author\/James-Carr"}]}},"_links":{"self":[{"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/posts\/816","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/users\/19"}],"replies":[{"embeddable":true,"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/comments?post=816"}],"version-history":[{"count":0,"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/posts\/816\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/media\/187"}],"wp:attachment":[{"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/media?parent=816"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/categories?post=816"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.javacodegeeks.com\/wp-json\/wp\/v2\/tags?post=816"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}