I'm uploading an image in base64 ( dataURL
) to an application that uses express. As the user is doing the "clipping" of this image in the front end I did not find another way to send but by dataURL
... the application has a general limit of 2mb by bad upload, the validation of the limit of this image would be 250Kb .
Searching I found numerous ways to do this validation among which I am (per hour) applying the following strategy:
- apply a
RegExp
to check if the string is adataURL
- retrieve the string part encoded in base64 using
split()
- decode the base64 to extract the length of the raw data
// função para decodificar o base64
function atob(str) {
return new Buffer(str, 'base64').toString('binary')
}
// a string (dataURL)
let avatar = req.body.avatar
// regex
let BASE64_REGEX = /^(data:\w+\/[a-zA-Z\+\-\.]+;base64)$/gi
// dividir
let arr = avatar.split(','),
mime = arr[0].match(/:(.*?);/)[1], // obter o mime-type
isBase64 = BASE64_REGEX.test(arr[0]) // testar
// decodificar e obter o comprimento dos dados brutos
console.log( 'size is: ' + atob(arr[1]).length )
Searching a little more to see if you could "do better" found this article which reports that it is not necessary to" do all this juggling "and these two topics in SO ( topic A , topic B ) that show the formula to get to the length of the file.
I decided to put this formula into practice as follows:
// a string (dataURL) (simplificado sem verificação)
let avatar = req.body.avatar.split(',')[1]
// armazenar como referência os dois últimos caracteres da string (para checar o padding)
let pad = avatar.slice(-2)
// definir o número de bytes para extrair (baseado no padding)
let padlen = (pad === '==') ? 2 : ((pad.slice(-1) === '=') ? 1 : null)
// calcular segundo a fórmula
console.log( 'size is: ' + ((avatar.length / 4) * 3 - padlen) )
As expected in both ways the result is the same:
size is: 72055
Link to the test at rextester.com
The question itself: It is not how to calculate but the cost of this calculation
As this is a "template" that can be used in other parts of the application and since I am not experienced in optimization, using the Buffer
approach would be "more costly" (consume more resources) than using slice()
and perform the math operation?
Thanks for any help ... and knowing the rules of the community, I'm not looking for answers based on opinion. A qualified response with sources or test model (or reference to one) would be welcome. Thankful.