Skip to main content
Blog
Home/

Pro tips for working with composite templates

Author Nima Poulad
Nima PouladSenior Developer Advocate
Summary3 min read

Get tips for avoiding common pitfalls when adding documents to composite templates.

    • Additional resources

    Table of contents

    Composite templates is an extremely useful feature that allows one to break their agreements in smaller and reusable modules. However, this powerful feature comes with complexity and, if not used correctly, will cause confusion and perhaps even frustration.

    As discussed in a previous blog, composite templates follow a set of rules when overlaying a set of composites on top of each other. The feature will apply these rules quietly in the back end and may ignore the documents or nondocument contributions that violate those rules—such as “first in, wins” when working with documents and “last in, wins” when dealing with nondocument contributions. The API won’t return an error if it ignores any of the provided data; you’re just given the result after the application of heuristics.

    As such, it becomes very important to understand the pitfalls fully when working with composite templates. If you’re not getting the output you were expecting from your composite templates, it can be difficult to try and understand what you did wrong. Hence, it’s better that we go over these pitfalls here to try and avoid any confusion altogether.

    Avoid providing the document via the InlineTemplate::documents field. In order to make your templates clean and easy to follow, always provide the document either via a serverTemplate or just by adding one on the fly with CompositeTemplate::document. If you have multiple documents to add, it might be tempting to use InlineTemplates::documents as it takes an array of documents. However, you should instead try the following:

    {
    ...
        "compositeTemplates": [{
            "document": {
               "documentId": "1",
               "name": "document-A",
               "fileExtension": "pdf",
               "documentBase64": "JVFS...NFRg=="
            }
        },
        {
            "inlineTemplates": [{
            "recipients": {
                "signers": [{
                   "email": "RandomTest1@example.com",
                   "name": "Random Tester1",
                   "tabs": {
                      ...
                   }
                }]
            },
            "sequence": "1"
            }]
        },
        {
            "document": {
               "documentId": "2",
               "name": "document-B",
               "fileExtension": "pdf",
               "documentBase64": "JztFS...geE=="
            }
        },
        {
            "inlineTemplates": [{
            "recipients": {
                "signers": [{
                   "email": "RandomTest2@example.com",
                   "name": "Random Tester2",
                   "tabs": {
                      ...
                   }
                }]
            },
            "sequence": "1"
            }]
        },
    ...
    ]}

    Where a document is followed by an inlineTemplate that can specify who the signers are as well as tabs and any other nondocument properties.

    At this point you may be wondering why the inlineTemplate::document resource exists. The answer is, it exists for legacy reasons only. You are always better off avoiding using it all together.

    Lastly, always remember that there is a “first in, wins” rule when it comes to adding documents. If your composite is providing a document via CompositeTemplate::document first followed by a serverTemplate that also has a document, then the ServerTemplate’s document will be ignored. Inversely, the same goes for nondocument contributions that follow a “last in, wins” policy.

    Additional resources

    Author Nima Poulad
    Nima PouladSenior Developer Advocate

    Nima Poulad has many years of experience in the industry as a software developer and as an advocate. He enjoys meeting the members of developer community and passionate about sharing what he knows with others. Find him on LinkedIn.

    More posts from this author

    Related posts

    • Developers

      How to call the Navigator API from Agentforce for smarter agreements

      Author Paige Rossi
      Paige Rossi
      How to call the Navigator API from Agentforce for smarter agreements
    • Configuring Salesforce for scalable and secure Docusign integrations

      Author Achille Jean Axel Nisengwe
      Achille Jean Axel Nisengwe
      Configuring Salesforce for scalable and secure Docusign integrations
    • 2025 Developer Release 1: Build faster, agree smarter

      Author Amina Atlaf
      Amina Atlaf
      2025 Developer Release 1: Build faster, agree smarter

    How to call the Navigator API from Agentforce for smarter agreements

    Author Paige Rossi
    Paige Rossi
    How to call the Navigator API from Agentforce for smarter agreements

    Configuring Salesforce for scalable and secure Docusign integrations

    Author Achille Jean Axel Nisengwe
    Achille Jean Axel Nisengwe
    Configuring Salesforce for scalable and secure Docusign integrations

    2025 Developer Release 1: Build faster, agree smarter

    Author Amina Atlaf
    Amina Atlaf
    2025 Developer Release 1: Build faster, agree smarter

    Discover what's new with Docusign IAM or start with eSignature for free

    Explore Docusign IAMTry eSignature for Free
    Person smiling while presenting