Nodejs 提供多个文件和 JSON 数据

Nodejs serve multiple files and JSON data

我正在使用 Nodejs 和 Angular 实现一个电子商务网站。 我有一些产品,每个产品都有多张图片和一些信息(价格,名称等)。

目前在我的MongoDB数据库中,我存储的是图片的绝对路径,以下是我目前API获取的单品。

router.get("/:productId", async (req, res, next) => {

  const result = await product_service.product_get(req.params.productId); 
  //'result' contains the product object
  //example: {price: 10, name:"test", images["D:/img1.jpg", "D:/img2.jpg"]}
  
  if (!result) { // err object is null, report error
          console.log(err)
          root_controller.req_fail(res, err.message)
      } else {
          // instead of absolute path provide the image path 
          // so that frontend can directly request it 
          for (var filePath of product.images) {
              if(fs.existsSync(filePath)) {
                  res.send(result); // here i need to append somehow the pictures to the response as well as the result object
              }
              else {
                  root_controller.req_fail(res, "File not found");
              } 
          }   
      }
      next();
  });

如何管理这种情况?

提前致谢!

The first one is I get the error: Cannot set headers after they are sent to the client.

res.writeHead(200, {
  "Content-Type": "application/octet-stream",
  "Content-Disposition": "attachment; filename=" + path.basename(filePath)
}); // First here
fs.createReadStream(filePath).pipe(res); // second streaming to res object

这是因为您发送了两次响应。

The second is that the image is in the body of my response and I lose all the other info (price, name etc...)

从代码中我看不到您正在向 res 对象添加信息。同样在这段代码中,如果找不到文件,则首先在 else 块中发送 res 两次,而无论 else 是否运行,都会执行另一个。你应该这样做:

router.get("/:productId", async (req, res, next) => {

  const result = await product_service.product_get(req.params.productId) 
  
  if (!result) { // err object is null, report error
          console.log(err)
          root_controller.req_fail(res, err.message)
      } else {
          // instead of absolute path provide the image path 
          // so that frontend can directly request it 
          for (var filePath of product.images) {
              if(fs.existsSync(filePath)) {
                  // here i need to append somehow the pictures to the response
                  // add URL in the response object with other details 
                  // create a model that can be helpful
                  const product = new Product(product.price,product.info and so on );
                  res.send(product);
              }
              else {
                  root_controller.req_fail(res, "File not found");
              } 
          }   
      }
      next();
  });

只是一个建议:不要将图像保存在服务器上,而是使用 AWS S3 存储桶或 Azure blob,并在特定产品的响应对象中提供 URLs。即使您想将图像存储在服务器上,也请向前端提供 URL 以便它可以请求资源。