12

Versioning in SendGrid allows API clients to make template requests only by template ID documented here, however, only one version of a template can be "Active" at a time. Obviously, the template used for our production applications needs to always be set to active, but what about adding a new template version we use in an upcoming release? How can I leverage template versions to test this "Inactive" version in our test environment? The issue was discussed here, but it seems to just be closed and lost when you start following the links.

If there is no way to specify versioning, that only leaves a few options that require either creating environment specific templates and having them get promoted to the production specific template once a release is finished, or creating separate accounts for different SDLC environments and migrating them as the process moves forward.

The issue was also discussed here in regards to language versioning, but it really doesn't help my problem.

What is the best practice given the tools provided by SendGrid's API to leverage versioning? Having different SDLC step named template seems like a disaster to maintain with hundreds of templates(let alone multiple for each environment). Managing multiple accounts just seems like a nightmare when it comes to testing when moving to production. Am I just missing something completely obvious here?

CodeKiller
  • 375
  • 4
  • 12

4 Answers4

9

I spoke with technical reps at SendGrid and this feature is not available from their API or UI. Only a single template can be "activated" at a time. You need a separate template for every environment, or the templates need to be managed from your API consumer. If anyone reads this and has questions about different solutions, feel free to post and I'll explain how I resolved this for my application`s needs.

CodeKiller
  • 375
  • 4
  • 12
5

There is apparently undocumented method to handle this.

I have some library code that parses the dynamic template's handle bar logic and programmatically injects the minimum amount of data needed to bind any variables. so that at design time if we wish it is possible to add any random item you like in the template with out updating the backend each time.

so it's critical with all that logic on the backend to make sure the delivered email is actually the same versioned i bound data against and I don't refresh my cache that often so . . .

having dug into this a little bit today,

I don't see it documented any where in any of sendgrids repos or documentation so the functionality will likely change or break in the future but you may use:

{"template_id": "d-#{template-guid}.#{version-guid}"

to control which version of the template is used in the v3/send/mail call.

Keith Brings
  • 241
  • 3
  • 5
2

We are two years on from the original post to this question and I have to say that, although SendGrid is good to use and easy enough to integrate, the way we are supposed to work with versions and multiple email templates is appalling.

We have 20 email templates. What we need to be able to do is modify a template (create a new version) and then test it through our environments. As things stand it is near on impossible to work this through different environments without affecting production.

Twillio need to sort this out.

  • 1
    Our company is currently looking to move off SendGrid, not only because it's a bugfest, but also because of this very technical limitation. It's ridiculous that SendGrid is so behind in so many domains. – Guillaume F. Dec 06 '22 at 10:16
1

I want to expand an actual answer by our implementation for small email campaigns

As CodeKiller wrote one of the possible workarounds is You need a separate template for every environment

The problem is application is referencing the template by id, but you can't preserve template id when moving template from env to env.

You can preserve the template name. SendGrid API doesn't allow retrieving templates by name instead you can retrieve all templates and find one by name.

var templatesRaw = await client.RequestAsync(
            BaseClient.Method.GET,
            null,
            "{'page_size': 200, 'generations': 'dynamic'}",
            "templates");
var templatesJson = await templatesRaw.DeserializeResponseBodyAsync(templatesRaw.Body);
var templates = (JArray)templatesJson["result"];

var template = templates.Single(templ => templ["name"].ToString() == name);
return template["id"].ToString();

Why I wouldn't recommend using it for medium/big campaigns:

  1. Cost if you go serverless. You'll pay for resources needed to process all your templates when you need to send one email
  2. Performance. Every time you need to send one email user is waiting for processing all templates
  3. Manual copy-pasting templates from env to env when template is created/updated
  4. KISS violation. It looks simple when you have <200 templates otherwise you have to deal with querying all templates from paginated API, possible OutOfMemory exceptions, batching email requests to prevent high cost/performance rates that eventually will complicate application.