Skip to content

Commit

Permalink
Node Server can now accept base64 images with validation and will sav…
Browse files Browse the repository at this point in the history
…e an image locally.
  • Loading branch information
chadstewart committed Mar 10, 2022
1 parent f2c9c67 commit 3d796ea
Show file tree
Hide file tree
Showing 11 changed files with 133 additions and 28 deletions.
12 changes: 6 additions & 6 deletions misc/api-spec.yaml
Expand Up @@ -38,9 +38,9 @@ paths:
type: string
format: binary
400:
description: Bad Request
description: This is not a properly formatted base64 image
415:
description: This media type isn't supported
description: Please send an image that is .jpg, .jpeg, .jpe or .png
500:
description: Unexpected error
get:
Expand Down Expand Up @@ -78,9 +78,9 @@ paths:
type: string
format: binary
400:
description: Bad Request
description: This is not a properly formatted base64 image
415:
description: This media type isn't supported
description: Please send an image that is .jpg, .jpeg, .jpe or .png
500:
description: Unexpected error
get:
Expand Down Expand Up @@ -135,9 +135,9 @@ paths:
type: string
format: binary
400:
description: Bad Request
description: This is not a properly formatted base64 image
415:
description: This media type isn't supported
description: Please send an image that is .jpg, .jpeg, .jpe or .png
500:
description: Unexpected error
get:
Expand Down
1 change: 1 addition & 0 deletions misc/examples/base64-img-example.txt

Large diffs are not rendered by default.

47 changes: 47 additions & 0 deletions misc/examples/base64-server-example.js
@@ -0,0 +1,47 @@
/*
* @Author: Pankaj Kumar.
* @Date: 17 June 2019
* @Source : https://jsonworld.com/
* @Topic : base-64-image-upload
*/

const express = require("express");
const app = express();
const port = 3000;
const bodyParser = require("body-parser");
const fs = require("fs");
const mime = require("mime");

// parse application/x-www-form-urlencoded
app.use(bodyParser.urlencoded({ extended: false }));

// parse application/json
app.use(bodyParser.json());

const uploadImage = async (req, res, next) => {
// to declare some path to store your converted image
var matches = req.body.base64image.match(/^data:([A-Za-z-+/]+);base64,(.+)$/),
response = {};

if (matches.length !== 3) {
return new Error("Invalid input string");
}

response.type = matches[1];
response.data = new Buffer(matches[2], "base64");
let decodedImg = response;
let imageBuffer = decodedImg.data;
let type = decodedImg.type;
let extension = mime.extension(type);
let fileName = "image." + extension;
try {
fs.writeFileSync("./images/" + fileName, imageBuffer, "utf8");
return res.send({ status: "success" });
} catch (e) {
next(e);
}
};

app.post("/upload/image", uploadImage);

app.listen(port, () => console.log(`Server is listening on port ${port}`));
2 changes: 1 addition & 1 deletion nodejs/src/app.ts
Expand Up @@ -5,7 +5,7 @@ const app = express();

//Initialize Request Data Type
app.use(express.json());
app.use(bodyParser.json());
app.use(bodyParser.json({ limit: '50mb' }));

//Intialize Routers
import indexRouter from "./routes/index-routes";
Expand Down
18 changes: 7 additions & 11 deletions nodejs/src/controllers/image-controller.ts
@@ -1,14 +1,10 @@
import {Request, Response} from "express";
import validateRequestIsImg from "../utils/validate-request-img";

const wrongContentErrorMsg = "Please send an image that is .jpg, .jpeg, .jpe or .png";
import { Request, Response } from "express";
import { prepareData } from "../utils/prepareData";
import { decodeAndStoreImg } from "../utils/decodeAndStoreImg";

export function imageResize (req: Request, res: Response) {
const isValidRequestType = validateRequestIsImg(req);

if(isValidRequestType) {

}

return res.status(400).send(wrongContentErrorMsg);
const matches = prepareData(req, res);
const isMatchesAnArray = Array.isArray(matches);
if(isMatchesAnArray) return decodeAndStoreImg(matches, res);
return matches;
};
22 changes: 22 additions & 0 deletions nodejs/src/utils/decodeAndStoreImg.ts
@@ -0,0 +1,22 @@
import mime from "mime";
import fs from "fs";
import { Response } from "express";

export function decodeAndStoreImg(matches: RegExpMatchArray, res: Response) {
const response = {
type: matches[1],
data: Buffer.from(matches[2], "base64")
}

let decodedImg = response;
let imageBuffer = decodedImg.data;
let type = decodedImg.type;
let extension = mime.extension(type);
let fileName = `image-${Date.now()}.${extension}`;
try {
fs.writeFileSync(`images/${fileName}`, imageBuffer, "utf8");
return res.send({ status: "The image was successfully uploaded!" });
} catch (error) {
throw (error);
}
}
4 changes: 4 additions & 0 deletions nodejs/src/utils/errorMessages.ts
@@ -0,0 +1,4 @@
export const errorMessages = {
notAnJpegOrPng: "Please send an image that is .jpg, .jpeg, .jpe or .png",
notBase64Structured: 'This is not a properly formatted base64 image'
}
18 changes: 18 additions & 0 deletions nodejs/src/utils/prepareData.ts
@@ -0,0 +1,18 @@
import { Request, Response } from "express";
import { errorMessages } from "../utils/errorMessages";
import validateRequestIsBase64Format from "../utils/validate-base64-request";
import validateRequestIsImg from "../utils/validate-request-is-img";

export function prepareData(req: Request,res: Response) {
const isThereABase64StringVariable = 'base64String' in req.body;
if(!isThereABase64StringVariable) return res.status(415).send(errorMessages.notBase64Structured);

const { base64String } = req.body;
const foundMatches = validateRequestIsBase64Format(base64String);
if(!foundMatches) return res.status(400).send(errorMessages.notBase64Structured);

const isCompatibleImage = validateRequestIsImg(foundMatches[1]);
if(!isCompatibleImage) return res.status(415).send(errorMessages.notAnJpegOrPng);

return foundMatches;
}
17 changes: 17 additions & 0 deletions nodejs/src/utils/validate-base64-request.ts
@@ -0,0 +1,17 @@
export default function validateRequestIsBase64Format (base64String: string) {
if (base64String === '' || base64String.trim() === '') return false;

const base64StructureRegex = (/^data:([A-Za-z-+/]+);base64,(.+)$/);
const isBase64StructuredString = base64StructureRegex.test(base64String);

if(isBase64StructuredString) {
const foundMatches = base64String.match(base64StructureRegex);
if(foundMatches) {
const isNotFormattedCorrectly = foundMatches.length !== 3;
if(isNotFormattedCorrectly) return false;
return foundMatches;
}
}

return false;
}
10 changes: 0 additions & 10 deletions nodejs/src/utils/validate-request-img.ts

This file was deleted.

10 changes: 10 additions & 0 deletions nodejs/src/utils/validate-request-is-img.ts
@@ -0,0 +1,10 @@
import validImageTypes from "./valid-img-types";

export default function validateRequestIsImg (dataType: string) {
for(const [key, value] of Object.entries(validImageTypes)) {
const isValidDataType = dataType === key;
if(isValidDataType) return true;
}

return false;
}

0 comments on commit 3d796ea

Please sign in to comment.