T

TechIdea

Ecosystem

Back to Tally Masterclass

How to Send JSON Data to TallyPrime

Convert standard JSON webhooks into Tally XML strings and automate data entry. Perfect for Shopify, Razorpay, or n8n integrations.

The Problem with JSON and Tally

When a customer buys a product on your Shopify store or makes a payment via Razorpay, those platforms send out a JSON Webhook. However, TallyPrime does not understand JSON. It only accepts XML POST requests on its HTTP server.

To integrate the two, we must build a translator (Middleware) that catches the JSON webhook and maps it into Tally's exact XML structure.

What we will build

An Express.js endpoint that accepts a JSON POST request representing a "Sale", converts it into Tally Voucher XML, and pushes it directly into Tally.

Step 1: The Incoming JSON Payload

Let's assume your external app sends this simple JSON object when a sale happens:

{
  "orderId": "INV-1024",
  "customerName": "Rohan Sharma",
  "amount": 5000,
  "date": "2026-07-09"
}

Step 2: The XML Mapping Function

We need a JavaScript function that takes this JSON and injects it into a Tally XML template for an Accounting Voucher.

const mapJsonToTallyXml = (data) => {
  // Format date for Tally (YYYYMMDD)
  const tallyDate = data.date.replace(/-/g, ''); 

  return `<ENVELOPE>
    <HEADER>
      <TALLYREQUEST>Import Data</TALLYREQUEST>
    </HEADER>
    <BODY>
      <IMPORTDATA>
        <REQUESTDESC>
          <REPORTNAME>Vouchers</REPORTNAME>
        </REQUESTDESC>
        <REQUESTDATA>
          <TALLYMESSAGE>
            <VOUCHER VCHTYPE="Sales" ACTION="Create">
              <DATE>${tallyDate}</DATE>
              <VOUCHERTYPENAME>Sales</VOUCHERTYPENAME>
              <PARTYLEDGERNAME>${data.customerName}</PARTYLEDGERNAME>
              <NARRATION>Order ID: ${data.orderId}</NARRATION>
              
              <!-- Debit Customer -->
              <ALLLEDGERENTRIES.LIST>
                <LEDGERNAME>${data.customerName}</LEDGERNAME>
                <ISDEEMEDPOSITIVE>Yes</ISDEEMEDPOSITIVE>
                <AMOUNT>-${data.amount}</AMOUNT>
              </ALLLEDGERENTRIES.LIST>
              
              <!-- Credit Sales Account -->
              <ALLLEDGERENTRIES.LIST>
                <LEDGERNAME>Sales Account</LEDGERNAME>
                <ISDEEMEDPOSITIVE>No</ISDEEMEDPOSITIVE>
                <AMOUNT>${data.amount}</AMOUNT>
              </ALLLEDGERENTRIES.LIST>
              
            </VOUCHER>
          </TALLYMESSAGE>
        </REQUESTDATA>
      </IMPORTDATA>
    </BODY>
  </ENVELOPE>`;
};

Step 3: The Webhook Receiver

Now, let's create the Express endpoint that catches the webhook, calls our mapping function, and posts it to Tally.

const express = require('express');
const axios = require('axios');
const app = express();
app.use(express.json());

const TALLY_URL = 'http://localhost:9000';

app.post('/webhook/new-sale', async (req, res) => {
  try {
    const saleData = req.body;
    console.log("Received new sale JSON:", saleData);

    const xmlPayload = mapJsonToTallyXml(saleData);

    const tallyResponse = await axios.post(TALLY_URL, xmlPayload, {
      headers: { 'Content-Type': 'text/xml' }
    });

    console.log("Tally Response:", tallyResponse.data);

    res.json({ success: true, message: "Sale pushed to Tally successfully." });
  } catch (error) {
    console.error("Error pushing to Tally:", error.message);
    res.status(500).json({ success: false, error: "Failed to push to Tally" });
  }
});

app.listen(3000, () => {
  console.log('Webhook receiver running on port 3000');
});

Important Considerations for Production

  • Auto-Creation of Ledgers: What if "Rohan Sharma" does not exist in Tally? The XML above will fail. In production, you must either check if the ledger exists first, or use TDL to force Tally to auto-create the ledger if missing.
  • Error Queues: What if Tally is closed when the webhook arrives? The data will be lost. You should use a database or queue (like Redis or RabbitMQ) to store the JSON payloads until Tally successfully processes them.
  • GST and Inventory: The simple voucher above is just an accounting voucher. If you need to deduct stock items and calculate IGST/CGST, the XML structure becomes significantly more complex.

Want it Automated Perfectly?

Handling GST calculations, item mapping, and offline queues in XML is difficult. Let our experts build a bulletproof JSON-to-Tally integration for your exact business logic.

Growth Newsletter

Get practical AI tools, SEO tips, and growth guides weekly.

Join creators, students, and businesses scaling with TechIdea.