Using Dynamic URLS to access Static Resources
I think we’ve all been guilty of hardcoding URLs at some time – I tend to do it when I’m whizzing through some development and I’m too in the zone to do things properly. I’ll just come back and fix it once I’m out of the zone.
Other times you’re linking static resources and things get moved, changed, etc. This is what happened to us over the weekend.
It’s always best practice to dynamically link your static resources. Take this jQuery code to drop a marker on a map:
marker = new google.maps.Marker({ position: coords, map: map, draggable: true, animation: google.maps.Animation.DROP, raiseOnDrag: true, icon: '{!URLFOR($Resource.PWSImages,'PWSImages/GeoLocate-PWS.png')}', title:"You are Here" });
Here I’m referencing a file inside of a zip archive, so I’m using the URLFOR() method. Your parameters are the name of the Resource to use (in this case, PWSImages) and the path to the file desired (PWSImages/GeoLocate-PWS.png).
My preference is always to contain related resources within the same archive, but sometimes you may wish upload a single file as a static resource. The syntax for that would be:
marker = new google.maps.Marker({ position: coords, map: map, draggable: true, animation: google.maps.Animation.DROP, raiseOnDrag: true, icon: '{!$Resource.GeoLocate-PWS}', title:"You are Here" });
…assuming of course you named the image resource “GeoLocate-PWS”.
Of course, this best practice isn’t limited to static resources. I’d say the second trickiest place is in email templates. For example:
If I have an object called Special Waste Profile triggering the email I can use the Detail Link mergefield: {!Special_Waste_Profile__c.Link}
But if the email is being triggered by a different object, and the email contains a link to a Special Waste Profile, things get tricky. First I need to create a Formula Text field on the opportunity called Server URL with the formula:
LEFT($Api.Partner_Server_URL_360, FIND( '/services', $Api.Partner_Server_URL_360))
Then in the email template I would use the following:
{!Triggering_Object__c.Server_URL__c}{!Special_Waste_Profile__c.Id}
Here’s how you can use dynamic links in other scenarios:
- Utilizing managed packages: ‘/apex/Namespace_PageName’
- Referencing Apex pages: ‘/apex/PageName’
- When linking an edit form for a a record we can also use the aforementioned URLFOR() method:
{!URLFOR($Action.Opportunity.Edit, opportunity.id)}
This way I can always be sure my links are dynamic and will not break on me.