Two alternative ways of developing and testing CloudPages

As a Salesforce Marketing Cloud developer, you have certainly been caught up in this loop: Develop the CloudPage > Save and Publish > Wait 2, 3 or even 5 minutes > Check the results. Moreover, if you are not debugging correctly, you can lose a lot of time between looking for the problem and waiting for your updates to propagate on your CloudPage. I must take this opportunity to invite you to check out Zuzanna’s article about debugging AMPScript in CloudPages, it is very helpful and well explained.

In this article, we will be covering two ways of testing your code on a CloudPage without having to wait for the propagation of changes every time we save and publish our work. These two ways are probably well know by experimented Salesforce Marketing Cloud developers, or by those who were fortunate enough to stumble upon some answers regarding this problem on Salesforce Stack Exchange.

Create an external web page

If you already have a web server, that is great. You can use it to create your web pages. However, if you are on a budget, or you just do not want to spend money on a hosting service, don’t worry, I have done the heavy lifting for you.

We are going to use awardspace.com, an ad-free hosting which offers:

  • Free subdomain
  • 1GB disk space
  • Up to 4 websites (websites and not pages)

Those features are more than enough for our tests. Especially because we can use one or two pages only and overwrite their content every time we need to develop a new CloudPage.

Step 1: Create a freehosting account

Go to awardspace.com and click on FreeHosting on the homepage:

Create an account using one of the available options:

Step 2: Creating a free subdomain

Go to Hosting Tools > Domain Manager. Select “Create a free subdomain”, fill in the subdomain’s name, and click Create:

Step 3: Creating the web page

Go to Hosting Tools > File Manager. Double click on your subdomain’s folder:

Click on Create and check Create file. Give it a name like sfmc.html for example.

Step 4: add content and access the web page

Congrats, we have successfully created the web page. Double click on it to add the content. Click save when done editing The web page’s URL is as shown below without the /home/www/ part.

Call the page from within Salesforce Marketing Cloud

We are going to use two AMPScript functions to access our external page from within our CloudPage.

  • HTTPGet: Returns the content from our external web page. This function will only take our web page URL as a parameter.
  • TreatAsContent: Treats the content returned by the HTTPGet function as it came from a content area. This way, we make sure the AMPScript code in our web page gets evaluated.

For example, our CloudPage on Marketing Cloud should contain something like: [see code snippet]

Each time we need to update the code, we just have to update it on the external web page. No need to save and publish our CloudPage as its content will remain the same.  

This way, we are avoiding the wait time between the publishing and the propagation of our changes on the servers when using a traditional development method.

Content Block By Key / Name / Id

The second method is using one of the three functions above. These functions return the content stored in the specified Content Block.

First, we will start by creating our Content Block. We need to go to Content Builder > Create > Content Blocks > Code Snippet.

I highly suggest using a Code Snippet instead of an HTML Content Block in order to avoid Content Builder’s editor from truncating parts of our HTML code.

Once we have created our Content Block and added our content in it. Time for getting it’s Key, Id or Name depending on which function we are using. We can find it by clicking on the drop-down icon and select Properties.

Now, we can head in to our CloudPage and add the code below: [see code snippet]

It pretty simple and straightforward. The code uses ContentBlockByKey to get our Content Block’s content. This is a onetime operation. Every time we need to update our code, we will only have to update it on the Content Block. This way, the updates are instantly live and we do not have to wait several minutes for the propagation on the servers.

Once we are done testing, we can copy the code on the external page or on the Content Block to our main CloudPage in Marketing Cloud and publish it.


About the author

Rachid Mamai is a SFMC geek and a Digital Marketing enthusiast living in France. To get in touch with Rachid, visit his LinkedIn.

Subscribe to Automation Studio notifications via SOAP API

If you have used Automation Studio to build workflows on autopilot, you are certainly aware of the importance of monitoring. Checking manually the execution status of every automation in your account is tedious and exhausting. Sometimes, you need to be notified in real time so you can fix eventual issues. That is why having email notifications enabled on your automations is necessary.

There are two types of notifications to which you can subscribe on automation settings:

  • Error or skipped run: you will receive an email if the automation’s execution fails or is skipped
  • Run Completion: you will receive an email once the automation’s run completes.

Keep in mind that at this moment, the only official way of interacting with Automation Studio via API is through SOAP. I’m saying “official” because there are actually some undocumented, but very limited, REST endpoints that can be used to play with Automation Studio. Let me know in the comments if you are interested.

Therefore, if we check the official SOAP documentation, we will see that creating an automation along with activities and email notifications in its settings is pretty easy and straightforward. However, if we look closer, we will find a comment on the notification tag saying: DOES NOT WORK. But we are not going to accept this for an answer, aren’t we?

This is the SOAP request sample from the documentation to create an automation: [see code snippet on Github]

To find the source of the problem, we should get into the tags responsible for adding email notifications to the settings. In this example, they are using a wrong value for the NotificationType tag in addition to a missing ChannelType tag.

NotificationType should be either “Complete” OR “Error” and definitely not “-1”. And ChannelType should be equal to 1.

The correct SOAP request to create an automation along with a “Complete” notification email should look like this: [see code snippet on Github]

For the curious ones, you may be asking how I found the working values. I invite you to go to Automation Studio, open the Chrome Developer Tools (F12) and click on the Network tab.

Open an automation, add your email to the settings and click done. Now go check out the Network tab. There is a REST call to the endpoint below.

Given the fact that we can only interact with Automation Studio using SOAP calls for now, we can understand why the endpoint is beta and not officially documented:

https://mc.s50.exacttarget.com/rest/beta/automations/notifications/AUTOMATION_ID/

Now let us look at the request payload:

We can see that the values used for NotificationType and ChannelType are as described above. That was worth a try and it worked: [see code snippet on Github]

I invite you to check the network tab every time you need to interact with Salesforce Marketing Cloud APIs. It can be very interesting and full of undocumented information.

If you know someone that can correct this on the official documentation, please get in touch through the comments or send me a message on LinkedIn.


About the author

Rachid Mamai is a SFMC geek and a Digital Marketing enthusiast living in France. To get in touch with Rachid, visit his LinkedIn.

Get Journey history by filtering the Definition ID via API

In today’s article, we will be going through a non-documented way of getting journey’s history through the API. The majority of this information is available on the UI. However, having a second way of getting this data in raw format can be helpful in some use cases. You can use free software like POSTMAN to interact with Marketing Cloud’s API and follow the steps in this article.

Let’s start by setting the correct scopes in Salesforce Marketing Cloud.

Set scope on Contacts and Journeys

When requesting our access token, we need to provide scopes used by our API calls. Do not forget to enable the Journeys & List and Subscribers scopes on the Installed package. We will be using these two scopes to get our journey’s history. Check out “Introduction to SFMC APIs” article for in-depth information about Installed packages setup and Salesforce Marketing Cloud APIs.

We need to set the scopes on the payload to get our access token: [see code snippet on Github]

Get Journey’s Definition ID

In this step, we will be getting information about a specific journey. The undocumented endpoint “interaction” provides access to a range of data, including the DefinitionID. Before getting into it, let me explain the differences between the three different identifiers of a journey:

  • Id: A unique id of the journey assigned by the journey’s API during its creation
  • Key: A unique id of the journey within the MID. Can be generated by the developer
  • DefinitionId: A unique UUID provided by Salesforce Marketing Cloud. Each version of a journey has a unique DefinitionID while the Id and Key remain the same.

Since the journey’s history is version dependent, we will be using DefinitionID to get history of a specific version.

Let us start by making a call to the below endpoint using name=JOURNEY_NAME as a URL parameter. By default, mostRecentVersionOnly parameter is set to true, therefore, the call will return information of the most recent version of the journey. Use VersionNumber=VERSION_NUMBER and mostRecentVersionOnly=false to get information about a specific version. Note that more parameters are available but not covered in this article since irrelevant: [see code snippet on Github]

The DefinitonID is located in a nested array called items, something like: [see code snippet on Github]

Get Journey’s history by filtering via Definition ID

We are finally there. In this step, we will call the endpoint below: [see code snippet on Github]

The payload should be something like below. Do not forget to set the Content-type as application/json on the call’s parameters: [see code snippet on Github]

You can apply multiple filters by setting different variables in the payload. In this example, we are selecting history data for our journey starting from October 23, 2019 to now. The journey is identified by the DefinitionID in the DefinitionIds array parameter in the payload. Other filters are:

  • Page and PageSize: For results pagination. The page starts from one.
  • Extras: represents a list of additional data to fetch. Available values are all, activities, outcomes and stats.
  • OrderBy: You can order by CreatedDate
  • MostRecentVersionOnly: To get information about the most recent versio of the journey. Accepts a true or false value.

This call will return something like below depending on the payload: [see code snippet on Github]


About the author

Rachid Mamai is a SFMC geek and a Digital Marketing enthusiast living in France. To get in touch with Rachid, visit his LinkedIn.