Skip to content

Instantly share code, notes, and snippets.

@taylorstine
Created March 11, 2017 15:04
Show Gist options
  • Select an option

  • Save taylorstine/ab4abc7b2d8cbce0868eac220b4b5c71 to your computer and use it in GitHub Desktop.

Select an option

Save taylorstine/ab4abc7b2d8cbce0868eac220b4b5c71 to your computer and use it in GitHub Desktop.
Validates an image request
import urlJoin from 'url-join'
import async from 'async'
import _ from 'lodash'
//We don't want an image bigger than this
const MAX_IMAGE_SIZE = 36000;
/**
* Validate a request to resize the image. Call multiple validators.
*/
export const validateRequest = (req, res, next)=>{
async.applyEachSeries([
validateHeaders,
validateUrlParams,
validateResizeRequest
], req, res, next);
};
/**
* validate a basic request. Ensure we have the header
* that tells us the hostname for the image
*/
export const validateHeaders = (req, res, next)=>{
const imageHost = req.header("Resizer-Image-Host");
if (!imageHost) {
return next(new Error("Resizer-Image-Host header must be provided"));
}
res.props = {
...res.props,
imageHost
};
next();
};
/**
* validates the size parameters of the url
*/
const validateResizeRequest = (req, res, next)=>{
const {size} = req.params;
const sizeSplit = size.split('x');
let widthValue = parseInt(sizeSplit[0]);
let heightValue = parseInt(sizeSplit[1]);
const widthError = validateSize(widthValue);
const heightError = validateSize(heightValue);
if (widthError && heightError) {
return next(new Error(`Sizes are not valid, got ${size}`))
}
if (widthError) {
widthValue = null;
}
if (heightError) {
heightValue = null;
}
res.props = {
...res.props,
height: heightValue,
width: widthValue,
};
next();
};
const validateSize = (size)=>{
if (!_.isFinite(size)) {
}
if (!_.inRange(size, 1, MAX_IMAGE_SIZE)) {
return new Error(`Size ${size} is out of range`);
}
};
/**
* Validates that we have all of the required parts of the url
*/
const validateUrlParams = (req, res, next)=>{
const {image:imageRoot, revision} = req.params;
const image = _.trimEnd(urlJoin(imageRoot, req.params[0]), '/');
if (_.isNil(image)) {
return next(new Error(`An image must be supplied, got ${image}`))
}
const revisionValue = parseInt(revision);
if (!_.isFinite(revisionValue)) {
return next(new Error(`A revision number must be supplied, but got ${revision}`))
}
res.props = {
...res.props,
image,
revision: revisionValue,
};
next();
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment