Re: $TriggerObject usage according to documentation

Anonymous
Not applicable

I'm researching an implementation of an email script that accesses custom objects and noticed the "$TriggerObject" in this documentation​​​. Although, the documentation seems to suggest that I should see the Trigger Object fields in the UI because it says:

When using the $TriggerObject, fields must be checked in the editing pane for the object in order to be made available to the script.

The email script edit pane requires you to check the fields that you want to use, but there is no reference to a trigger object? I've triggered an email through the "Added to {Custom Object Name}" trigger (the documentation mentions this) and attempted to access fields on the "$TriggerObject" (like the documentation), but it appears the TriggerObject is not defined?

My hope is that I could access the "Edge" object in this type of setup​, but I can't figure out what "$TriggerObject" is and if it really exists. I tried the following where "groupClassRegistration" is my "Bridge" object and it's field is checked in the script editor for debugging purposes.

ID1: ${TriggerObject.marketoGUID}

<br/>

ID2: ${TriggerObject.MarketoGUID}

<br/>

Else: ${groupClassRegistrationV2_cList.get(0).marketoGUID}

21 REPLIES 21
Anonymous
Not applicable

Hi Maheswar Gunampally,

Product is not directly associated to the Lead.

Product represents a library of products we currently sell. It stores product names, costs, descriptions. There's one record for each unique product. We wanted a many-to-many relationship between Lead and Product, hence the intermediary object Product Interest, but we want to maintain only one record for each Product.


The idea behind this is to be able to use the Product table in email tokens, and to be able to segment the DB on past Product Interests. We also want one instance of each Product, so that we can make updates to them that are used across the board (i.e. change a course cost)

According to developers.marketo.com;

"You can reference first and second level custom objects that are directly connected to the Lead, Contact, or Account, but not third-level custom objects. " - Email Scripting » Marketo Developers

I may be misunderstanding this but I take it as the first level custom object would be Product Interest, and the second level is Product, so I assumed this would work.

Add Marketo Custom Object Link Fields - Marketo Docs - Product Docs covers creating the objects in the way I have, which works within Smart Lists just fine, but the Product data is not available in the Email Scripting engine.

I'm not sure why they wouldn't let you do this, as it would be incredibly useful for personalising emails, rather than using a multitude of snippets.


Cheers,

Alex

Mark_Westerman
Level 2

I have exactly the same requirement. I would really like to know how other people personalize their emails with Product information when they have hundreds of products.

SanfordWhiteman
Level 10 - Community Moderator

I store the product catalog in its own Velocity token (as a VTL/Java ArrayList, i.e. a JSON-like array of objects).

Then we do lookups into that array from our other Velocity tokens.

Mark_Westerman
Level 2

This sounds interesting. How is this done?

What is a Velocity token?

Is there a separate Velocity token for each product?

Can this information be imported or does it have to keyed in directly?

SanfordWhiteman
Level 10 - Community Moderator

What is a Velocity token?

"Email Script" tokens are written in Apache Velocity Template Language (VTL).

Is there a separate Velocity token for each product?

No, one token. That token defines one $variable (an ArrayList) that holds the product catalog.

Can this information be imported or does it have to keyed in directly?

You can use the API to write the token if you want.

Mark_Westerman
Level 2

I have hacked some code that you have posted in a different discussion but it is returning the default value rather than the value that matches the CourseCode on the Lead. Am I on the right track? I know this code originally related to a custom object. This is the code I am using and I expected to match on 5522US.

## Set up your map of Courses to related asset(s) 

#set( $assetsByCourse = { 

  "5522US" : { 

    "OCBURL" : "http://www.csu.edu.au/courses/bachelor-of-science-honours

  }, 

  "1105PP" : { 

    "OCBURL" : "http://www.police.nsw.gov.au/recruitment/home

  }, 

  "" : { 

    "OCBURL" : "http://www.csu.edu.au/courses

  } 

} ) 

## 

## Start w/default asset set (empty key) 

#set( $assets = $assetsByCourse[""] ) 

## 

## Guard against bad inputs (null or empty object list) 

#if( $LeadList && !$LeadList.isEmpty() ) 

    ## 

    ## Loop backwards through objects (standard for each is fwd only) 

    #foreach( $idx in [$math.sub($LeadList.size(),1)..0] ) 

        #set( $Lead = $LeadList[$idx] ) 

        #foreach( $assetSet in $assetsByCourse.keySet() ) 

            ## 

            ## If we find a regex match for [map key,CourseCode] we're done 

            #if( $Lead.CourseCode.matches("(?i)${assetSet}") ) 

                #set( $assets = $assetsByCourse[$assetSet] ) 

                #break($foreach.parent) 

            #end 

        #end 

    #end 

#end 

"${assets.OCBURL}"

SanfordWhiteman
Level 10 - Community Moderator

What about a dump of $LeadList? Can't tell you what should match unless I see the input.

Mark_Westerman
Level 2

Sorry, I am new to this. I am just trying to send an email to a lead and include a url to the course they are interested in based on the Course Code on the Lead. I have had to resort to coding this because Marketo doesn't provide a way to insert a field from a custom object that is not directly related to the Lead.

Capture.PNG

SanfordWhiteman
Level 10 - Community Moderator

OK, so you don't have a $LeadList (array of COs) in this case, so nothing to iterate over. CourseCode is just a property on the Lead: $Lead.CourseCode

        #foreach( $assetSet in $assetsByCourse.keySet() ) 

            ## If we find a regex match for [map key,CourseCode] we're done 

            #if( $Lead.CourseCode.matches("(?i)${assetSet}") ) 

                #set( $assets = $assetsByCourse[$assetSet] ) 

                #break($foreach.parent) 

            #end 

        #end 

Mark_Westerman
Level 2

this is my modified script

## Set up your map of Courses to related asset(s) 

#set( $assetsByCourse = { 

  "5522US" : { 

    "OCBURL" : "http://www.csu.edu.au/courses/bachelor-of-science-honours

  }, 

  "1105PP" : { 

    "OCBURL" : "http://www.police.nsw.gov.au/recruitment/home

  }, 

  "" : { 

    "OCBURL" : "http://www.csu.edu.au/courses

  } 

} ) 

## 

## Start w/default asset set (empty key) 

#set( $assets = $assetsByCourse[""] ) 

## 

## Guard against bad inputs (null or empty object list) 

        #foreach( $assetSet in $assetsByCourse.keySet() ) 

            ## If we find a regex match for [map key,CourseCode] we're done 

            #if( $Lead.CourseCode.matches("(?i)${assetSet}") ) 

                #set( $assets = $assetsByCourse[$assetSet] ) 

                #break($foreach.parent) 

            #end 

        #end 

"${assets.OCBURL}"

It is still not giving my the correct url. I did notice that when I drag the Lead field over to the script editor in Marketo the syntax is ${lead.courseCode}.

SanfordWhiteman
Level 10 - Community Moderator

Yes, you should use Marketo's names for the fields and properties -- and they are case-sensitive. I can't know the site-specific names.

Mark_Westerman
Level 2

I understand.

I am not sure which version I should use;

If I use (without the curly brackets)

  #if( $lead.courseCode.matches("(?i)${assetSet}") )

I get this error

An error occurred when procesing the email Rendered_Email_Velocity_Error_Area_?!

$foreach.parent is not a valid org.apache.velocity.runtime.directive.Scope instance near

?

If I use exactly as it inserts from Marketo

#if(${lead.courseCode}.matches("(?i)${assetSet}") )

I get this error

An error occurred when procesing the email Body!

Lexical error, Encountered: "m" (109), after : "." at *unset*[line 177, column 36] near

            ## If we find a regex match for [map key,CourseCode] we're done  
            #if(${lead.courseCode}.matches("(?i)${assetSet}") )  
                #set( $assets = $assetsByCourse[$assetSet] )  
                #break($foreach.parent)  
            #end  
SanfordWhiteman
Level 10 - Community Moderator

Use the first one (second is bad syntax) but I see the extra loop is referenced in there. Just use #break, not #break(<loopname>).

Mark_Westerman
Level 2

That does the job, thanks so much for your patience

SanfordWhiteman
Level 10 - Community Moderator

Great! If you have other questions please open new threads -- it's easier and clearer for later searches.

Anonymous
Not applicable

Hi Blaine,

So you are using "Added to {Custom Object Name}" trigger. $TriggerObject is the 'custom object' that triggered this smart campaign.

Say you want to do something when a new record is added to a custom object named 'Edge', you will then use,

Trigger: Added to EDGE custom object trigger.

The $TriggerObject will contain a recordset with values of the newly added record for this EDGE object.

And you will need to make sure that the fields of the object EDGE you want to use in the email script are 'checked' in the RHS pane.

For example, if you have a 'courses registered' custom object. And you have API programming set up to insert new record in this custom object when a lead registers for a course on your website. And let's say you want to send them email 'Here are the course materials' for 'that' course, then you will do,

Trigger:

Added to Courses Registered custom object

Flow:

Send email

Email:

Will contain email script merged with $TriggerObject fields. These fields will display values of the 'actual course that person registered for now'.

Does it make sense? Does it answer your question?

Rajesh Talele

Anonymous
Not applicable

Hi Rajesh,

Thanks for your reply.

So in your example, is "Course Registered" the only custom object? I have something like:

Lead -> Course Registration -> Course

and the triggers show up as "Added to Course" but I don't see any "Course" fields in the RHS pane of the email script editor, only fields for "Course Registration".

Anonymous
Not applicable

Hello Blaine,

not sure if you solved this, I will give it a try. You have 2 custom objects linked to the LeadId. Do you any common ID that you can link back to ?

Here is what we did in our case.

Lead                             Course                   CourseReg          

Lead ID                         CourseId               RegId

CustomerID(CRM)       CustomerId           CourseId   

                                     CourseName         RegDate, Paid etc   

So Course has all the information related to the course and CourseReg has the information related to registration(event). Now you want to send out a welcome email on Registration to the student.

SmartList : (Triggered)

Added To CourseReg

Flow:

Send Email

-------------------------------------------------------------------------

In order to get the Course information, you capture the CourseId from the triggered event and loop in the Course.

Token for the email.

Reg Id : $!{TriggerObject.RegId}

Course Id : $!{TriggerObject.CourseId}

##get Course Name

#set($list =  ${Course_cList})

#foreach( $value in $list)

    #if( ${value.CourseId} == $!{TriggerObject.CourseId} )

     #set($CourseTitle =  ${value.CourseTitle})

     ## you can get all the vaues form the customObject here.

     #end

#end

Hope that helps.

- Mahesh

Anonymous
Not applicable

Hi Maheswar Gunampally,

Why do you have the customer ID connected to the Course and not to the Course Reg?

I would have expected your objects to look like

Lead                             Course                       CourseReg         

Lead ID                         CourseId                    RegId

CustomerID(CRM)          CourseName              CourseId  

                                     Course Cost               CustomerID (or Lead ID)

                                                                      RegDate, Paid etc  

So there would only ever be 1 instance of each course, and if you made updates to the list of courses you'd just batch API update, or send support a csv file. You'd then have CourseReg being created via API (potentially looping back from a webhook request out of Marketo via a proxy of some sort).

It doesn't appear possible to access CourseName via email scripting with this set up, even though the 'TriggerObject' as shown in the interface would be the Course, and not the CourseReg.

Any thoughts on how you'd make this work?

Cheers,

Alex

Anonymous
Not applicable

Alex ,

is your product custom object linked to lead? I believe it has to be associated by the link to show. I could be wrong. we have implemented CourseReg object with course related fields. We did not push the Course to MKTO, only have the Course which customer purchased and attributes that are needed.

We have CourseReg and Payment. When email is sent to customer on payment we need show the CourseTitle. When payment object is pushed we only know the CourseId. we go back to CourseReg to get its title and other data as needed.

Hope it helps.

- Mahesh