Get Size of a FormData Object Payload

OpenJavaScript 0

Last updated: February 17, 2023.

There are two general approaches to estimating the size of a FormData object:

  1. Aggregate the size of all attached items
  2. Get its overall size as a payload sent to a server

Though getting overall size may seem like the best solution because it takes into account everything on the payload, this may be inappropriate in some use cases.

For example, you may not want to hold a user accountable for exceeding an overall file size limit because of information contained on the FormData object for which they are not responsible. For example, text that exists to help the receiving server interpret the contents of the payload.

First, let’s create a FormData object from input provided by the user on the frontend:

<body>

    <label for="name">Enter name:</label><br>
    <input type="text" id="name"><br>

    <input type="file" accept="image/*"><br>

    <button type="submit">Submit</button>

</body>

<script>

    const textInput = document.querySelector('input[type="text"]');
    const fileInput = document.querySelector('input[type="file"]');

    document.querySelector('button').addEventListener('click', () => {

        const fd = new FormData();
        fd.append('username', textInput.value);
        fd.append('user-file', fileInput.files[0]);

        // Now, calculate size here
        
    })

</script>

Now, let’s do both calculations:

Estimating size by attached items

On a FormData object, there are two possible types of data: text and file data.

Text data is stored in UTF-8 format, which means that one character usually represents one byte of data, but not always. So it is best to place any text values inside a Blob object and then query its size property, which provides this value in bytes.

For files, a size property is already available without the need for this step.

Given this, it follows that you can estimate the size of a FormData object by iterating through each item attached to it and conditionally calculating size dependent upon data type.

For each item that is calculated, the bytes value should be added to a variable, which, after iteration is complete, will express the value of all items.

Assuming a FormData object named fd, here’s how to code it:

let bytes = 0;
for (item of fd) {
    if (typeof item[1] === 'string') {
        bytes += new Blob([item[1]]).size;
    } else {
        bytes += item[1].size;
    }
}
console.log(bytes);
console.log(bytes/1024); // in kB

Estimate overall payload size

The strategy here is to simulate the FormData object in a payload and then its size.

This is easy enough by placing it in a Response object (what you would usually get back initially when making a fetch request) and reading its contents to Blob format:

const response = new Response(fd);
response.blob()
.then(blob => console.log(blob.size))

If you are curious about what the FormData object looks like, read the response object to text:

const response = new Response(fd);
response.text()
.then(text => console.log(text))

For example, for some text input and a small image the payload looks like this as text:

-----------------------------16240366515315408623518946556
Content-Disposition: form-data; name="user"
Bob
-----------------------------16240366515315408623518946556
Content-Disposition: form-data; name="user-file"; filename="image.jpg"
Content-Type: image/jpeg
������Exif��II*���������������������������V�����������^���(�����������������������i�������f�������H�������H�����������������0210��������������������������������0100��������������������d�����������d�������ASCII���Picsum ID: 106���C�����������		�
��
����������������� $.' ",#��(7),01444�'9=82<.342���C�			����
�2!�!22222222222222222222222222222222222222222222222222������d�d��"�����������������������������������������������������������������������������:��|���{��V\���Ο�Ʉ�ޏ91w�x��o))�W~z�-����IR9�$I�?5.��R��0��Y��������<ƛI��Gq��1v��\�Vj*��6�����Q���aiOLa\Rn߯/���&��������������������������� �!0�"#13�����������r����7�?�f�����������l|��9h���j'���<�̪ؗ�� �����As������ue���P�7��F����с��!mG̟�x�`��]�n��sa
B�<;�t����w}y]�3 �!��k����$�'����JPy7��
����/m����ǰ���ʆs�!���&�a����r�RמJb&E�=]6,V濷*�D,��C�c~,��W�6���}AM`l�A����9	�������aSY��)k	�ڮ#�p.d��My���|Ș*7���������-<��,f�d"ū��3rzSz�Qr��t�c����g@36H��[�����Y`����I���F����$�����������������������!1A�� �"2Qa��������?����f�l[����O����#t�����6�.�i�S�v��P6�)��wN����-.������ؠ�7�d�3&���'��q��ۂ��:4��vL�*򏤠D�B�����ŸM��ΪI�v�u��
-2�Ħ@���M�®�n�������'��������������������!1A�Qaq�ё���� ����������?!"��:&�*e��ܹpz�A�=.\�-���+�1�ω_0��,_��9�0�R��g�ܾ��yʏ�J۴���ҮH��X������|��z���;FD������,̱]�w��L#�5�yT9�_�)-v�9��L�0a�]G��-�ܐ�7�$�
�S,�����g}����hˤ���P������7�'���B�d�\A��r�'P�*��O
u�8H獹�������C�������E�-����?�0��V��V�䌫�3A���|����=�_���]]�?0A)>�0`��@�a��>�J�R͟���[�V���ό������1��%@�W{Yz����
����ר�����ad���)	�ݡ�CJ[���lu�}{"���)^����N�U*�x{�@�[�L�G�1Э����E��hyA���s�(���}�E�)Xb��lAO����������!����	h��6�*�tӋ�����7��!�+���br��l&߈p���D��j�"��[�*����%����P�ͰSa����:�o��g�%.�J|PMm�⩖)�^ҍ�N�&t�W��J�WEfcMGr���gU�SV�a2���>�Q������B�K ,a`�#����R�Ů���-��}���>�g��������������������Y�A����F��,yh�3$s"������_�@�'�8�	������$��������������������1!AQ�q���a������������?��pe��`��`#������]�w�����������B\k�U������}�V�.a�����~!��?�Tp��|�ı~?X�����!@�岆�}7��#�.��X�F�5����͇�	�l+�����%s�����"��������������������!1AQ���a������������?��$Ϩ��[�g�d��2z����h�$:���x	�8��� +����ы���G��ѐs���BǑ����˽�"������l���Y|��K���W�%���M��'��s;�������$��������������������!1AQaq����������������?��p�T�k��$��������e����\��QU���T�"��"h���
��p�����X�(�ȗ1(�V���ÿ��
��Eq0���p�H�O�$� ������%A
�j���_0�ji�t���	cL������̭8J�+�kFq��n����.�UUꝃQ���9�BQ]����)�������f "ଠ��1T0j\�
�����
�ہAu��\ˡ!����D��nz��}�iP�[-�fS�S�/�qO��=��6��0SLQ{��
�e<�[���.���,�kS#�¥7���e��F2��5��]rY��&�P�0���l�&���/�nۤ�"lje�1�\`�������u�n�(��q�qvnf�b��A� j�0\��N�;hS�q�JR�eZ%�Q��m4%���z��E�s��o�џP�^�S�q�����6�������N��R�JYsPl�	MJ∔��,�j5S+�SO��j[
��Z�������A��(Jr�U�����jj���iƏ��Q¶O���2�AK,����u�8"Sw��r��%�ʸ���H$x�������B�s�\S����՝��G�,�l���q���2�5���kp4����=L� �S4��ff�:R'��{����Ε����-�P��s���,�Kӡ��D6���;�����le�+�ݮ��3����
��#�f��;}3����g����&	A'�x�\��r���c�b��#�U�Y��J��
 �r�|�*����g���F���/b���6�5�F�|���:��Z�N��vL�*h�ǚ����aײ���-;�� ���%7Y��Wn1�����a����ͷ0 �k�Ce�f����}�h��ȩ�o�?��[��~�P�\��^���aj��������/�ЦB��I��J�r�u���ۇ��
�.����=��]r���ixҪ�"�t�T���4[��8�E����:�?�����00r���������Gڼ���Y6dZ�[� ��I���:�#J���s�L�Tj�iK�+!
0���
-----------------------------16240366515315408623518946556--

On the payload, file data is sent in binary format. The size of the string above does not equal the size of the data on payload. For this, you should call blob() on the Response object containing the payload, as shown previously.

Notice the additional text providing metadata for the payload and each item. In contrast to the measurement of individual items, this is taken into account when measuring the overall payload size.

Related posts