Json to htmlTable

Describe the issue/error/question

I am trying to take a json input and output it as a HTML table.
Found the below JAva info to use but I do not know how to modify it to work in a Function Node.

In this case there is dummy data but I would like to replace that with the previous nodes Json data going forward?

What is the error message (if any)?

Please share the workflow

(Select the nodes and use the keyboard shortcuts CMD+C/CTRL+C and CMD+V/CTRL+V to copy and paste the workflow respectively)

Share the output returned by the last node

Information on your n8n setup

  • **n8n version:0.156.0
  • **Database you’re using (default: SQLite):sqlite
  • Running n8n with the execution process [own(default), main]:
  • Running n8n via [Docker, npm, n8n.cloud, desktop app]:

Any assistance would be appreciated.

Hi @mvandyk, I think the easiest way of building an HTML table in n8n would be via the Spreadsheet File node.

Here’s an example workflow, if you just need the binary file you wouldn’t need the last Move Binary Data node. The Function node only sets dummy data in this example, so would also not be required when working with actual data:

Example Workflow

Thanks, I saw this Example.

I would like thr result to go into a “Webhook Reply” as a table? Could I do this without the spreadsheet file as I need to keep time down? I have made a workaround for my scenario (where I only have 3 columns

In Set I just add the html table tabs “{{$node[“Http”].json[“item1”]}}” in the end I add the rest of the html detail

Hi @mvandyk,
I’m trying to get to the same solution than you. Did you achieve to complete?

Hi @MaaPer, sorry for not following up here. You can actually use the example with a Webhook node as well, simply put the Webhook node in the front and a Respond to Webhook node in the back returning the HTML:

Now when visiting the Webhook node’s URL, you’ll get a HTML table in response:

image

As for the response time, this takes less than 0.2 seconds for me to run:

1 Like

My final target is to embed one airtable data set on to the mail body with table format.
So that, my interest is to obtain the formatted data from the web hook and copy paste on gmail node as HTML format so the receiver will see the info within the mail.

I will try with you solutions, seems it could work.
The only thing is to apply some formatting to the headings and use the th tag instead td one. You you think could be possible?

Thanks in advance.

I see. The Spreadsheet File node doesn’t apply formatting or has detailed options for choosing the right HTML tags, so it’s probably not the best node for your job specifically.

However, you can still manually build the HTML you have in mind, for example like so:

This would send out an email like so:

image

1 Like

Cool thank you I will try as soon as possible and will let you know.
Thanks!

Yes, appreciate the help.

1 Like

works perfect!!!
will be great some kind of node to make the transformation easier.
in any case, thank you very much.

Sharing here an awesome little script Chat GPT helped me with to do just this. Very happy with the output which is very readable, even with a larger dataset.

function createTable(data, title) {
    if (!data || data.length === 0) {
        return '';
    }

    if (!Array.isArray(data) && typeof data === 'object' && data !== null) {
        data = Object.entries(data).map(([key, value]) => ({ key, value }));
    }

    let html = `<table>
<caption>${title}</caption>
<thead>
<tr>`;
    let headerKeys = Object.keys(data[0]);
    headerKeys.forEach(key => {
        html += `<th>${key}</th>`;
    });
    html += `</tr>
</thead>
<tbody>`;
    data.forEach(row => {
        html += '<tr>';
        headerKeys.forEach(key => {
            let cellValue = row[key];
            if (Array.isArray(cellValue) || (typeof cellValue === 'object' && cellValue !== null)) {
                cellValue = createTable(cellValue, '');
            }
            html += `<td>${cellValue}</td>`;
        });
        html += '</tr>';
    });
    html += `</tbody>
</table>`;
    return html;
}

function jsonToTable(jsonData) {
    let html = `<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>JSON to HTML Table</title>
    <style>
        body {
            font-family: Arial, sans-serif;
            margin: 0;
            padding: 20px;
        }
        table {
            border-collapse: collapse;
            width: 100%;
            margin-bottom: 20px;
        }
        table, th, td {
            border: 1px solid #ccc;
        }
        th, td {
            padding: 6px;
            text-align: left;
            vertical-align: top;
            border-top: 1px solid #ddd;
        }
        th {
            background-color: #f2f2f2;
            font-weight: bold;
        }
        tr:nth-child(even) {
            background-color: #f2f2f2;
        }
        caption {
            font-size: 1.2em;
            font-weight: bold;
            margin-bottom: 10px;
            margin-top: 20px;
        }

        /* Print styles */
        @media print {
            body {
                padding: 10px;
            }
            table, th, td {
                font-size: 12px;
            }
            caption {
                font-size: 1em;
            }
        }
    </style>
</head>
<body>
<div>`;
    if (!jsonData.error) {
        html += createTable(jsonData.sourcesUsed, 'Sources Used');
        Object.keys(jsonData.matches).forEach(matchKey => {
            let matchData = jsonData.matches[matchKey];
            if (matchData.length > 0) {
                html += createTable(matchData, `Matches - ${matchKey}`);
            }
        });
    } else {
        html += 'Error: No data to display.';
    }
    html += `</div>
</body>
</html>`;

    return html;
}

// Usage example
let jsonData = $input.first().json;
let tableHTML = jsonToTable(jsonData);
return { 
  html: tableHTML
};

the code gives out an error for some reason. " ```
TypeError: Cannot convert undefined or null to object

on this line `Object.keys(jsonData.matches).forEach(matchKey => {`