- Class:
com.dotcms.rendering.velocity.viewtools.content.ContentMap
- Reference Documents: Github, JavaDoc
$content.structure
$content.structure.fields ## Array List
- Class:
com.dotcms.rendering.velocity.viewtools.StructuresWebAPI
- Reference Documents: GitHub, JavaDoc
- Class:
com.dotcms.rendering.velocity.viewtools.content.BinaryMap
- Reference Documents: GitHub, JavaDoc
$content.binaryField.rawUri
Result: /contentAsset/raw-data/1234567890/binaryField
/contentAsset/image/$content.identifier/binaryField/filter/{filterName}/{filterValue}
$content.binaryField.rawUri
Result: /contentAsset/raw-data/1234567890/fieldBinary
$content.binaryField.name
- Class:
java.util.ArrayList
containingcom.dotmarketing.portlets.categories.model.Category
- Reference Documents: GitHub, JavaDoc
$categoryObject.name
Example:
#foreach ($category in $content.categoryField)
$category.name
#end
$categoryObject.categoryVelocityVarName
Example:
#foreach ($category in $content.categoryField)
$category.categoryVelocityVarName
#end
$categoryObject.key
Example:
#foreach ($category in $content.categoryField)
$category.key
#end
- Class:
com.dotcms.rendering.velocity.viewtools.content.CheckboxMap
- Reference Documents: GitHub, JavaDoc
$content.checkboxField.options
Result: ["Item 1", "Item 2"]
$content.checkboxField.values
Result: ["item-1","item-2"]
$content.checkboxField.selectedValues
Result: ["item-2"]
#if ($UtilMethods.isSet($content.checkboxField.selectedValues))
has selections
#else
no selections
#end
## Using contains()
#if ($content.checkboxField.selectedValues.contains("my-value"))
has my-value
#else
doesn't have my-value
#end
## Using indexOf()
#if ($content.checkboxField.selectedValues.indexOf("my-value") > -1)
has my-value
#else
doesn't have my-value
#end
- Class:
java.sql.Timestamp
- Ref for
java.sql.Timestamp
: JavaDoc - Reference Documents:
$date.format("MM/dd/YYYY hh:mm:ss a", $content.dateField)
$a.dateField.getTime()
$date.calendar.getTimeInMillis()
#set ($myDate = $date.toDate(1475594610991))
#set ($myCalendar = $date.toCalendar($content.dateField))
or convert string to date to pass into calendar
#set ($myCalendar = $date.toCalendar($date.toDate(1475594610991)))
#set ($myCalendar = $date.toCalendar($a.dateField))
#set ($dummy = $myCalendar.add(1, 3)) ## Add 3 years
3 Years from Now: $date.format("MMMM, d YYYY", $myCalendar)
#set ($dummy = $myCalendar.add(5, -90)) ## Subtract 90 days
90 Days Less than 3 Years From Now: $date.format("MMMM, d YYYY", $myCalendar)
- Class:
com.dotcms.rendering.velocity.viewtools.content.FileAssetMap
- Reference Documents: GitHub, JavaDoc
$content.fileField.uri
$content.fileField.shortyUrl
$content.fileField.host
$content.fileField.hostName
$content.fileField.fileName
$content.fileField.path
$content.fileField.size
$content.fileField.fileAsset.path
NOTE: Image field
metadata
property is a JSON formatted string, which can be converted into a useable JSON object
#set ($imageMetadata = $json.generate($a.imageField.metaData))
Result:
{"height":"1440","width":"2560","keywords":"stuff","contentType":"image/jpeg","fileSize":"201923"}
NOTE: Quality only works in JPEG images, which can be checked with the metadata object
Simple resizing and quality
## Resize to 400px (preserve ratio) width with 60% quality
$!{content.imageField.shortyUrl}/400w/60q
## Resize to 400px (preserve ratio) height with 60% quality
$!{content.imageField.shortyUrl}/400h/60q
## Resize to 640x400 (ratio not preserved)
$!{content.imageField.shortyUrl}/640w/400h
NOTE: File Asset identifier
identifier
orinode
NOTE: Processed images are cached
## Grayscale
/contentAsset/image/$!{a.imageField.identifier}/fileAsset/filter/Grayscale
## Resize
/contentAsset/image/$!{a.imageField.identifier}/fileAsset/filter/Jpeg/jpeg_q/50
## Chaining multiple filters
/contentAsset/image/$!{a.imageField.identifier}/fileAsset/filter/Rotate,Jpeg/rotate_a/180.0jpeg_q/50
- Class:
com.dotcms.rendering.velocity.viewtools.content.RadioMap
- Reference Documents: GitHub, JavaDoc
$content.radioField.options
Result: ["Item 1", "Item 2"]
$content.radioField.values
Result: ["item-1","item-2"]
$content.radioField.selectValue
Result: ["item-2"]
#if ($UtilMethods.isSet($content.radioField.selectValue))
has a selection
#else
no selection (null)
#end
#if ($content.radioField.selectValue == "my-value")
my-value is selected
#else
my-value not selected
#end
- Class:
java.util.ArrayList
ofcom.dotcms.rendering.velocity.viewtools.content.ContentMap
(s) - Reference Documents: Relationship Documentation
$content.relationshipField
## Loop through all related contentlets in field
#foreach ($con in $content.relationshipField)
Do things
#end
## Supply null or empty string
$dotcontent.pullRelatedField($content.identifier, "ContentType.relationshipField", $__null)
$dotcontent.pullRelatedField($content.identifier, "ContentType.relationshipField", "+ChildCT.title:HELLO")
NOTE: By default, order of related contentlets is dictated by the order in the field
$dotcontent.pullRelatedField($content.identifier, "ContentType.relationshipField", $__null, "modDate desc")
$dotcontent.pullRelatedField($content.identifier, "ContentType.relationshipField", $__null, 5, "modDate desc")
- Class:
com.dotcms.rendering.velocity.viewtools.content.SelectMap
- Reference Documents: GitHub, JavaDoc
$content.selectField.options
Result: ["Item 1", "Item 2"]
$content.selectField.values
Result: ["item-1","item-2"]
$content.selectField.selectValue
Result: ["item-2"]
#if ($UtilMethods.isSet($content.selectField.selectValue))
has a selection
#else
no selection (null)
#end
#if ($content.selectField.selectValue == "item-2")
item-2 is selected
#else
item-2 not selected
#end
- Class: Returns:
com.dotcms.rendering.velocity.viewtools.content.ContentMap$1
but is really ajava.util.HashMap
#foreach ($entry in $content.keyValueField.map.entrySet())
Key Name: $entry.key
Key Value: $entry.value
#end
/da/$content.imageField.identifier
TODO
- class:
java.util.ArrayList
- Reference Document: JavaDoc
#set ($myArr = [])
or
#set ($myArr = $contents.getEmptyList())
Result: []
#set ($myArr = [false, true, "one", 'two', 3 ])
contains(Object o)
$myArr.contains("one") ## True/False
#set ($myArr = ["zero", "first", "second", "third", "fourth"])
$myArr.indexOf("second")
Result: 2
$myArr.indexOf("nope")
Result: -1
#set ($myArr = ["zero", "first", "second", "third, "fourth"])
$myArr[2]
Result: second
$myArr.get(0)
Result: zero
size()
#set ($myArr = ["zero", "first", "second", "third, "fourth"])
$myArr.size()
Result: 5
NOTE: While a two-handed approach isn't always necessary, it will ensure the code is always executed
#set ($myArr = ["zero", "first", "second", "third", "fourth"])
#set ($dummy = $myArr.add("fifth"))
$myArr[5]
Result: fifth
#set ($dummy = $myArr.remove("fifth"))
$myArr
Result: [zero, first, second, third, fourth]
#set ($dummy = $myArr.remove(2))
$myArr
Result: [zero, first, third, fourth]
Classes:
- Using
{}
:java.util.LinkedHashMap
- Using
$contents.getEmptyMap()
:java.util.HashMap
Reference Documentation: java.util.LinkedHashMap
: JavaDocjava.util.HashMap
: JavaDoc
#set ($myMap = {})
or
#set ($myMap = $contents.getEmptyMap())
#set ($myMap = {
'Name': "Frank Lloyd Wright",
'Occupation': "Architect",
'birthplace': 'Richland Center, WI'
})
#set ($dummy = $myMap.put("prop", "value"))
#set ($dummy = $myMap.remove("prop"))
- Class:
java.lang.String
- Reference Document: JavaDoc
#set ($myString = "This $anotherString.") ## Contents will be parsed by Velocity
or
#set ($myString = 'This $anotherString.') ## Contents will not be parsed by Velocity
concat(String str)
## Starting with...
#set ($myString = "This is")
#set ($myString = "${myString} a complete sentence.")
or
#set ($myString = $myString + " a complete sentence.")
or
#set ($dummy = $myString.concat(" a complete sentence."))
indexOf(String str, int fromIndex)
#set ($myString = "This is a complete sentence.")
$myString.indexOf('complete')
Result: 10
$myString.indexOf('arse')
Result: -1
#set ($myString = "This is a complete sentence.")
$myString.length()
Result: 28
#set ($myString = "This is a complete sentence.")
$myString.contains('complete')
Result: true
$myString.contains('arse')
Result: false
substring(int beginIndex)
#set ($myString = "This is a complete sentence.")
$myString.substring(0, 15)
Result: This is a compl
replace(CharSequence target, CharSequence replacement)
replaceAll(String regex, String replacement)
#set ($myString = "abcdefghijklmnop")
$myString.replace("cde", '')
Result: abfghijklmnop
#set ($myString = "/this crappy url.html")
$myString.replaceAll("\s", "-")
Result: /this-crappy-url.html
#set ($myString = "abcdefg hijklmn op")
$myString.split(" ")
Result [abcdefg, hijklmn, op]
- Class:
com.dotcms.rendering.velocity.viewtools.VelocityRequestWrapper
- Reference Documents: GitHub, JavaDoc
$request.getHeader("Content-Type")
$request.setHeader("Location", "/404.html")
$request.getParameter("query")
#foreach ($header in $request.getHeaderNames())
Name: $header
Value: $request.getHeader($header)
#end
$request.getLocale()
Result: en_US
$request.getMethod()
$request.getRequestURI()
$request.getRequestURL()
$request.getScheme()
Result: https
$request.getServerPort()
Result: 443
$request.getAttribute('javax.servlet.forward.request_uri')
$request.setAttribute('javax.servlet.error.status_code', 404)
javax.servlet.forward.request_uri
javax.servlet.forward.context_path
javax.servlet.forward.servlet_path
javax.servlet.forward.mapping
com.dotmarketing.LOCALE
com.dotmarketing.frontend.locale
com.dotcms.repackage.org.apache.struts.action.MODULE
com.dotcms.directive.renderparams
CLICKSTREAM_RECORDED
com.dotmarketing.htmlpage.language.current
DOT_RULES_FIRED_ALREADY
idInode
com.dotmarketing.session_host
CMS_FILTER_URLMAP_OVERRIDE
$response.setStatus(404)
or
$response.sendError(500, "whoops!")
$response.sendRedirect("/login/")
$response.getHeader("Location")
$response.setHeader("Location", "/login/")
$response.addHeader("X-Forwarded-Proto", "https")
- Class:
com.dotcms.rendering.velocity.viewtools.VelocitySessionWrapper
- Reference Documents: GitHub, JavaDoc
$session.getId()
$session.getAttribute("com.dotmarketing.htmlpage.language")
$session.setAttribute("something", "neat")
$session.removeAttribute("something")
$session.setAttribute("cms.user", $cmsuser.getUserByUserId("userID"))
$session.invalidate()
com.dotmarketing.frontend.locale
com.dotmarketing.LOCALE
com.dotcms.visitor
browserSniffer
clickstream
com.dotmarketing.htmlpage.language
com.dotmarketing.session_host
- Reference Documents: JavaDoc
## By ID
#set ($user = $cmsuser.getUserById("userID"))
## By Email
#set ($user = $cmsuser.getUserByEmail("userID"))
## By Session
#set ($user = $cmsuser.getLoggedInUser($request))
## Get user map
#set ($userData = $user.getUserProxy())
#set ($userIsAdmin = $cmsuser.isCMSAdmin($user)) ## True | False
#set ($userHasRole = $user.isUserRole($user, "Role Name")) ## True | False
NOTE: This will only set a cookie in the current URI path context. If you need a cookie on "/", then do it in HTTP headers
$cookietool.add("name", "value", "age") ## age is optional
$cookietool.get("JSESSIONID")
$config.getStringProperty("propertyname", "defaultvalue")
$config.getBooleanProperty("propertyname", false|true)
$config.getIntProperty("propertyname", 6)
Other gets: getFloatProperty, getLongProperty, getStringArrayProperty
Character | Invoke |
---|---|
$ | $esc.d |
$ | $esc.dollar |
# | $esc.h |
# | $esc.hash |
" | $esc.q |
" | $esc.quote |
' | $esc.s |
' | $esc.singleQuote |
\ | $esc.backslash |
! | $esc.e |
! | $esc.exclamation |
- $esc.java()
- $esc.javascript()
- $esc.html()
- $esc.sql()
padToLength(String baseString, int finalLength, String padString)
#set ($str = "abcdefghij")
$UtilMethods.padToLength($str, 40, "-")
Result: abcdefghij------------------------------
#set ($emptyString = "")
$UtilMethods.isSet($emptyString)
Result: false
#set ($notEmptyString = "abc")
$UtilMethods.isSet($emptyString)
Result: true
#set ($emptyArray = [])
$UtilMethods.isSet($emptyArray)
Result: false
#set ($notEmptyArray = ["one", "two"])
$UtilMethods.isSet($notEmptyArray)
Result: true
#set ($str = "Lorem ipsum dolor sit amet")
$UtilMethods.capitalize($str)
Result: Lorem Ipsum Dolor Sit Amet
pluralize(long num, String word)
#set ($str = "result")
$UtilMethods.pluralize(2, $str)
Result: results
shortstring(String text, int maxNumberOfChars, boolean includeEllipsis)
$UtilMethods.shortstring($str, 50, true)
#set ($str = "http://www.google.com/")
$UtilMethods.encodeURL($str)
Result: http%3A%2F%2Fwww.google.com%2F
#set ($str = "http%3A%2F%2Fwww.google.com%2F")
$UtilMethods.decodeURL($str)
Result: http://www.google.com/
join(String[] strArray, String separator, boolean empty)
#set ($myArray = ["one", "two", "three", "four"])
$UtilMethods.join($myArray, " ") ## Will append seperator at end
Result: one two three four
#set ($myJson = $json.fetch("https://postman-echo.com/get?foo1=bar1&foo2=bar2", timeout, headers))
$myJson.args
Result:
{
"foo1": "bar1",
"foo2": "bar2"
}
#set ($myMap = {
'one': "one",
'two': "two"
})
#set ($myJson = $json.post("https://postman-echo.com/post", 10, headers, $myMap)) ## Can use put() instead of post()
Result: {"args":{"one":"one","two":"two"},"headers":{"content-length":"0","x-forwarded-proto":"https","host":"postman-echo.com","x-forwarded-port":"443","accept-encoding":"gzip,deflate","user-agent":"Apache-HttpClient/4.5.2 (Java/1.8.0_222)"},"data":{},"form":{},"files":{},"json":null,"url":"https://postman-echo.com/post?one=one&two=two"}
$import.read("https://www.google.com")
- Class:
com.dotcms.rendering.velocity.viewtools.CategoriesWebAPI
- Reference Documents: GitHub, JavaDoc
Category Object: com.dotmarketing.portlets.categories.model.Category
- Reference: JavaDoc
#set ($myCategory = $categories.getCategoryByKey("CategoryKeyName"))
#set ($myCategory = $categories.getCategoryByKey("CategoryKeyName"))
#set ($childCategories = $categories.getActiveChildrenCategories($myCategory))
- Class:
com.dotcms.rendering.velocity.viewtools.content.ContentTool
- Reference Documents: GitHub, JavaDoc
pull(String query, String limit, String sort)
#set ($content = $dotcontent.pull("+contentType:webPageContent", 0, "webPageContent.title asc"))
find(String inodeOrIdentifier)
#set ($specificContentlet = $dotcontent.find("identifier"))
pullRelated(String relationshipName, String contentletIdentifier, boolean pullParents, int limit, String sort)
NOTE: Legacy relationships will be removed from dotCMS at some point, use relationship fields instead. More information can be found in the Relationships field section.
## boolean pullParents set to true will pull parent contentlets from child side of relationship
#set $relatedContentlets = $dotcontent.pullRelated("ParentCT-ChildCT", "identifier", false, 0, "ChildCT.name asc")
| publish | b9d89c803d | | unpublish | 38efc763d7 | | archive | 4da13a425d | | delete | 777f1c6bc8 |
NOTE: Adding identifier will publish against an exiting contentlet NOTE: Invoking fire() inside a conditional does work. Exceptions will results in a falsy result.
#set ($myContentletMap = {
'stName': "MyContentType",
'title': "Hello world",
'description': "lorem ipsum",
'body": "<p>content!</p>"
})
$workflowtool.fire($myContentletMap, "b9d89c803d")
- Reference: JavaDoc
#set ($folderOjbect = $folderAPI.findCurrentFolder($VTLSERVLET_URI, $host))
$sorter.sort([5, 3, 7])
Result: [3, 5, 7]
$sorter.sort([ {"name": "zxy"}, {"name": "abc"} ], "name")
Result: [{name=abc}, {name=zxy}]
$sorter.sort([ {"name": "zxy"}, {"name": "abc"} ], "name:desc")
[{name=zxy}, {name=abc}]
$dotlogger.info("Something happened!")
Other Logging methods: warn(), error(), debug()
NOTE: dotCMS is preconfigured to transmit to a localhost mailserver. If you have postfix installed with default configuration (allowing messages from localhost), no additional configuration is requires
$mailer.sendEmail(String to, String from, String subject, String message, Boolean html)
$mailer.sendEmail("johnny5@gmail.com", "admin@example.com", "This is a test", "Testing 1-2-3", false)
#set ($emailHTML = "<h1>HELLO WORLD!</h1>")
$mailer.sendEmail("johnny5@gmail.com", "admin@example.com", "This is a test", $emailHTML, true)
Pro-tip: An easy programmer friendly is to compose your body markup is to use
#define
, then.toString()
your object when invoking$mailer.sendEmail()
#define ($emailHTML)
<h1>Hello World</h1>
<p>This is a <strong>test</strong> message. Pretty neat, eh?</p>
#end
$mailer.sendEmail("johnny5@gmail.com", "admin@example.com", "This is a test", $emailHTML.toString(), true)
- Class:
com.dotmarketing.portlets.calendar.viewtools.CalendarWebAPI
- Reference Documents: GitHub, JavaDoc
- dotCMS Calendar Documentation: https://dotcms.com/docs/latest/pull-calendar-events-nbsp-nbsp-i-calendar-find-i
findEvents(String hostId, Date fromDate, Date toDate, String tag, String keyword, String categoryInode, String sortBy, int offset, int limit)
- Class:
com.dotcms.rendering.velocity.viewtools.LanguageViewtool
- Reference Documents: GitHub, JavaDoc
$text.get("buttons.confirm")
$text.setLanguage(2)
- Class:
org.apache.velocity.tools.generic.MathTool
- Reference Documents: GitHub, JavaDoc
- dotCMS Documentation: https://dotcms.com/docs/latest/mathtool
$math.add(x, y)
$math.sub(x, y)
$math.mul(x, y)
$math.div(x, y)
$math.mod(x, y)
$math.pow(x, y)
$math.abs(x)
$math.max(x, y)
$math.min(x, y)
$math.ceil(x)
$math.floor(x)
$math.round(x)
$math.roundTo(x, y)
$math.getAverage(l)
$math.getTotal(l)
$math.getRandom()
$math.random(x, y)
$math.toDouble(x)
$math.toInteger(x)
#set ($num = 12.34)
$number.format ('currency', $num)
Result: $12.34
$number.format('integer', $num)
Result: 12
$number.toNumber("12")
Result: 12
- Class:
com.dotcms.rendering.velocity.viewtools.navigation.NavTool
- Reference Documents: GitHub, JavaDoc
- Navtool Documentation: https://dotcms.com/docs/latest/navtool-viewtool
- Nav item Result Class:
com.dotmarketing.viewtools.navigation.NavResult
orcom.dotcms.rendering.velocity.viewtools.navigation.NavResultHydrated
Returns a list of pages and file assets (based on parameters) that have "show on menu" enabled
NOTE: Does not respect asset permissions unless set in configuration
$navtool.getNav()
- Gets current level navigation
- Get specific navigation
getNav(Host host, String path)
getNav(int level)
getNav(String path)
getNav(String path, long languageId)
getFile(String identifier, boolean live, [long languageId])
#set ($file = $filetool.getFile("identifier", true))
#set ($file = $filetool.getFile("identifier", true))
$filetool.getURI($file)
$crypt.crypt("abc123")
Result: Z/FssgdeJ+YlY=
$crypt.decrypt("Z/FssgdeJ+YlY=")
Result: abc123
- Class:
com.dotcms.rendering.velocity.viewtools.DotRenderTool
- Reference Documents: GitHub, JavaDoc
- dotCMS Documentation: https://dotcms.com/docs/latest/rendertool
- Class:
com.dotcms.rendering.velocity.viewtools.WebsiteWebAPI
- Reference Documents: GitHub, JavaDoc
- Folder object:
com.dotmarketing.portlets.folders.model.Folder
- Reference: JavaDoc
Returns folder object
$website.getFolder("/path/to/folder", "hostID")
Returns list of subdirectory folder objects
$website.getSubFolders("/path/to/folder", "hostID")
#set ($myVar = "abc123")
#define ($myVar)
put whatever in here
#end
#dotParse ('/application/vtl/myfile.vtl')
#dotInclude ('/application/vtl/myfile.vtl')
#include ('/application/vtl/myfile.vtl') ## I think this is deprecated
#evaluate('#set ($str = "my string")')
#if ($something == "abc")
something is abc
#else ($something == "def")
something is def
#else
something is not abc or def
#end
NOTE: Macros are not functions, but you can fake it to some degree. See examples below
#macro (myMacro $param)
I am outputting $param
#end
#myMacro ("some text")
Result: I am outputting some text
#foreach ($item in $arr)
$foreach.index ## Index of iteration
$foreach.count ## Foreach iteration count (from 1)
$foreach.hasNext ## true / false
#end
#stop
#break
TODO
TODO
TODO
TODO
TODO
- Markdown ViewTool Class:
com.dotcms.rendering.velocity.viewtools.MarkdownTool
- Markdown ViewTool Reference Documents: GitHub, JavaDoc
NOTE:
getRaw()
returns unparsed text
$markdown.parse($content.getRaw("textField"))
$VTLSERVLET_URI ## Returns URI path of page as known from Virtual Heirarchy
$request.getRequestURI() ## Returns URI as requested by HTTP header
#macro (CoolThing $string)
<h1>I am macro outputting $string</h1>
#end
#set ($output = "#CoolThing(\"my string\")" ) ## Wrapping in single quotes will not parse
or
#set ($output = $render.recurse($context, "#CoolThing(\"my string\")"))
Ueeful if page break back-end previews
#set ($IS_BACKEND = false)
#if ($UtilMethods.isSet($session.getAttribute('com.dotmarketing.PAGE_MODE_SESSION')))
#set ($IS_BACKEND = true)
#end
or check for the following
$EDIT_MODE
$PREVIEW_MODE
$ADMIN_MODE
$LIVE_MODE
Wrap JSON with named object so it can be parsed properly. Unnamed objects will not parse with JsonTool
#set ($rawText = $import.read("https://example.com/api/json"))
#set ($jsonObject = $json.generate("{ \"data\": { $rawText }"))
#set( $list = $navtool.getNav("/") )
#foreach($n in $list)
#set($children = $n.children)
#if($children && $children.size() > 0)
<li class="has-dropdown">
<a href="#">${n.title} <b class="caret"></b></a>
<ul class="dropdown">
#foreach($ch in $children)
<li #if ($ch.active) class="active" #end><a href='${ch.href}'>${ch.title}</a></li>
#end
</ul>
</li>
#else
<li #if ($n.active) class="active" #end><a href='${n.href}'>${n.title}</a></li>
#end
#end
#foreach($key in $context.getKeys())
Key: $key | Value: $context.get($key)
#end
$render.eval("#dotInclude($webapi.getAssetPath('/path/to/file'))")
#dotParse("$filetool.getFile(${contentlet.fileAssetFieldName.identifier},true).getURI()")
$webapi.setVelocityVar("abc", 123)
$abc ## Output: 123
Or:
## Make sure to wrap this in a #set()
#set ($_ = $context.getVelocityContext().put("abc", 123))
$abc ## Output: 123