Parcourir la source

Make the API return more data + tests + doc

rigwild il y a 4 ans
Parent
commit
0ccac3fa81
4 fichiers modifiés avec 121 ajouts et 20 suppressions
  1. 27 3
      server/routes/getImage.js
  2. 50 7
      server/routes/getImageExtracts.js
  3. 17 5
      test/api/getImage.js
  4. 27 5
      test/api/getImageExtracts.js

+ 27 - 3
server/routes/getImage.js

@@ -2,6 +2,7 @@
 
 import express from 'express'
 import path from 'path'
+import sharp from 'sharp'
 import boom from '@hapi/boom'
 
 import { imagesPath, imageServedUrl } from '../../config'
@@ -30,6 +31,7 @@ const router = express.Router()
  * @apiSuccess {String} data.sceneName Scene name of the image
  * @apiSuccess {Number} data.quality Quality of the image
  * @apiSuccess {String} data.ext Extension of the image
+ * @apiSuccess {Object} data.metadata Metadata of the image, @see https://sharp.dimens.io/en/stable/api-input/#metadata
  * @apiSuccessExample {json} Success response example
  * HTTP/1.1 200 OK /api/getImage?sceneName=bathroom&imageQuality=200
  * {
@@ -38,7 +40,19 @@ const router = express.Router()
  *     "fileName": "bathroom_00200.png",
  *     "sceneName": "bathroom",
  *     "quality": 200,
- *     "ext": "png"
+ *     "ext": "png",
+ *     "metadata": {
+ *       "format": "png",
+ *        "width": 800,
+ *        "height": 800,
+ *        "space": "rgb16",
+ *        "channels": 3,
+ *        "depth": "ushort",
+ *        "density": 72,
+ *        "isProgressive": false,
+ *        "hasProfile": false,
+ *        "hasAlpha": false
+ *      }
  *   }
  * }
  *
@@ -143,8 +157,10 @@ export const getImage = async (sceneName, quality, nearestQuality = false) => {
     else imageData = sceneData.find(x => quality === x.quality)
   }
 
-  if (imageData)
-    return {
+
+  if (imageData) {
+    // Data gathered from file system
+    const result = {
       link: `${imageServedUrl}/${sceneName}/${imageData.fileName}`,
       path: path.resolve(imagesPath, sceneName, imageData.fileName),
       fileName: imageData.fileName,
@@ -153,6 +169,14 @@ export const getImage = async (sceneName, quality, nearestQuality = false) => {
       ext: imageData.ext
     }
 
+    // Data gathered by analysing the image
+    const input = sharp(result.path)
+    const metadata = await input.metadata()
+    result.metadata = metadata
+
+    return result
+  }
+
   // Image not found
   throw boom.notFound(`The requested quality "${quality}" was not found for the requested scene "${sceneName}".`)
 }

+ 50 - 7
server/routes/getImageExtracts.js

@@ -37,6 +37,13 @@ const router = express.Router()
  * @apiSuccess {String} data.info.sceneName Scene name of the original image
  * @apiSuccess {Number} data.info.quality Quality of the original image
  * @apiSuccess {String} data.info.ext Extension of the original image
+ * @apiSuccess {Object} data.metadata Metadata of the image, @see https://sharp.dimens.io/en/stable/api-input/#metadata
+ * @apiSuccess {Object} data.info.extractsConfig Configuration used to cut the image
+ * @apiSuccess {Number} data.info.extractsConfig.x Number of extracts per line (horizontal)
+ * @apiSuccess {Number} data.info.extractsConfig.y Number of extracts per row (vertical)
+ * @apiSuccess {Object} data.info.extractsSize Size of extracted images
+ * @apiSuccess {Number} data.info.extractsSize.width Width of the extracted images
+ * @apiSuccess {Number} data.info.extractsSize.height Height of the extracted images
  * @apiSuccessExample {json} Success response example
  * HTTP/1.1 200 OK /api/getImageExtracts?sceneName=bathroom&imageQuality=200&horizontalExtractCount=1&verticalExtractCount=2
  * {
@@ -46,11 +53,33 @@ const router = express.Router()
  *       "/api/images/bathroom/extracts/x1_y2/zone00002/bathroom_zone00002_200.png"
  *     ],
  *     "info": {
- *       "link": "/api/images/bathroom/bathroom_00200.png",
- *       "fileName": "bathroom_00200.png",
- *       "sceneName": "bathroom",
- *       "quality": 200,
- *       "ext": "png"
+ *       "extractsConfig": {
+ *         "x": 1,
+ *         "y": 2
+ *       },
+ *       "extractsSize": {
+ *         "width": 800,
+ *         "height": 400
+ *       },
+ *       "image": {
+ *         "link": "/api/images/bathroom/bathroom_00200.png",
+ *         "fileName": "bathroom_00200.png",
+ *         "sceneName": "bathroom",
+ *         "quality": 200,
+ *         "ext": "png"
+ *         "metadata": {
+ *           "format": "png",
+ *            "width": 800,
+ *            "height": 800,
+ *            "space": "rgb16",
+ *            "channels": 3,
+ *            "depth": "ushort",
+ *            "density": 72,
+ *            "isProgressive": false,
+ *            "hasProfile": false,
+ *            "hasAlpha": false
+ *          }
+ *       }
  *     }
  *   }
  * }
@@ -169,7 +198,11 @@ const cutImage = async (image, xExtracts, yExtracts) => {
         link: extractLink,
         path: extractPath,
         fileName: extractName,
-        sceneName: image.sceneName
+        sceneName: image.sceneName,
+        originalWidth: width,
+        originalHeight: height,
+        width: xCropSize,
+        height: yCropSize
       }
 
       // Check the file already exist
@@ -273,7 +306,17 @@ router.get('/', asyncMiddleware(async (req, res) => {
   res.json({
     data: {
       extracts: extracts.map(x => x.link),
-      info: image
+      info: {
+        extractsConfig: {
+          x: horizontalExtractCountInt,
+          y: verticalExtractCountInt
+        },
+        extractsSize: {
+          width: extracts[0].width,
+          height: extracts[0].height
+        },
+        image
+      }
     }
   })
 }))

+ 17 - 5
test/api/getImage.js

@@ -94,11 +94,23 @@ test('GET /getImage?sceneName=bathroom&imageQuality=10', async t => {
   t.is(res.status, 200, json(res))
   t.is(res.body.data.link, `${imageServedUrl}/bathroom/bathroom_00010.png`, json(res.body))
   t.deepEqual(res.body.data, {
-    'link': `${imageServedUrl}/bathroom/bathroom_00010.png`,
-    'fileName': 'bathroom_00010.png',
-    'sceneName': 'bathroom',
-    'quality': 10,
-    'ext': 'png'
+    link: `${imageServedUrl}/bathroom/bathroom_00010.png`,
+    fileName: 'bathroom_00010.png',
+    sceneName: 'bathroom',
+    quality: 10,
+    ext: 'png',
+    metadata: {
+      format: 'png',
+      width: 800,
+      height: 800,
+      space: 'srgb',
+      channels: 3,
+      depth: 'uchar',
+      density: 72,
+      isProgressive: false,
+      hasProfile: false,
+      hasAlpha: false
+    }
   }, json(res.body))
 
   // Check link is accessible and is an image

+ 27 - 5
test/api/getImageExtracts.js

@@ -115,11 +115,33 @@ test.serial('GET /getImageExtracts?sceneName=bathroom&imageQuality=10&horizontal
   t.true(Array.isArray(res.body.data.extracts), json(res.body))
   t.is(res.body.data.extracts[0], `${imageServedUrl}/bathroom/extracts/x5_y2/zone00001/bathroom_zone00001_10.png`, json(res.body))
   t.deepEqual(res.body.data.info, {
-    link: `${imageServedUrl}/bathroom/bathroom_00010.png`,
-    fileName: 'bathroom_00010.png',
-    sceneName: 'bathroom',
-    quality: 10,
-    ext: 'png'
+    extractsConfig: {
+      x: 5,
+      y: 2
+    },
+    extractsSize: {
+      width: 160,
+      height: 400
+    },
+    image: {
+      link: `${imageServedUrl}/bathroom/bathroom_00010.png`,
+      fileName: 'bathroom_00010.png',
+      sceneName: 'bathroom',
+      quality: 10,
+      ext: 'png',
+      metadata: {
+        format: 'png',
+        width: 800,
+        height: 800,
+        space: 'srgb',
+        channels: 3,
+        depth: 'uchar',
+        density: 72,
+        isProgressive: false,
+        hasProfile: false,
+        hasAlpha: false
+      }
+    }
   }, json(res.body))
 
   // Check link is accessible and is an image