Skip to the content
Documentation
Help Start
Reading in:
  • German: 9,059 of 9,059 pages
About the help in other languages
All help pages

Fetching content in templates

For CMS developers, the fetch functions that replace hand-written queries. It covers single nodes and objects, children and subtrees, class and attribute filters, sorting, paging with the offset view parameter, counts…

Download as PDF

Address: https://doc.exponential.earth/exphelp/viewer/help/cms-developers/fetching-content-in-templates.md

On this page

Fetching content in templates

This page is for developers who need lists and lookups in templates: the latest news, the events of next month, the children of a folder, related items. Templates do not run SQL; they call fetch functions that the modules define, and every fetch checks permissions, visibility and languages for you.

Contents

  1. The call
  2. The fetches you use most
  3. Children and subtrees
  4. Filtering by class and by attribute
  5. Sorting
  6. Paging
  7. Rules for fast fetches
  8. When a fetch is not enough

The call

{def $result = fetch( '<module>', '<function>', hash( '<parameter>', <value>, ... ) )}

The functions and their parameters are declared in each module's function_definition.php, for content in kernel/content/function_definition.php. Single results can be false (missing, or not readable by this user), so test them: {if $node}...{/if} (Fetch basics).

The fetches you use most

CallReturns
fetch( 'content', 'node', hash( 'node_id', 2 ) )one node (also by node_path or remote_id)
fetch( 'content', 'object', hash( 'object_id', 57 ) )one object
fetch( 'content', 'list', hash( ... ) ), list_countchildren of a node, and how many
fetch( 'content', 'tree', hash( ... ) ), tree_countall descendants, with depth limits
fetch( 'content', 'related_objects', hash( ... ) ), reverse_related_objectsrelations (Relations and embeds)
fetch( 'content', 'keyword', hash( ... ) )objects by keyword
fetch( 'content', 'search', hash( 'text', ... ) )search results (Search)
fetch( 'user', 'current_user' )the signed-in user
fetch( 'explayouts', 'resolve_layout', hash() )the layout of the current page (Layouts for CMS developers)

All content fetch functions with every parameter: Fetch functions reference.

Children and subtrees

The list and tree parameters (kernel/content/function_definition.php): parent_node_id, sort_by, offset, limit, depth, depth_operator, class_filter_type, class_filter_array, attribute_filter, extended_attribute_filter, main_node_only, ignore_visibility, language, only_translated, as_object, load_data_map, objectname_filter, group_by and limitation.

{def $news = fetch( 'content', 'list', hash(
        'parent_node_id', $node.node_id,
        'class_filter_type', 'include',
        'class_filter_array', array( 'article' ),
        'sort_by', array( 'published', false() ),
        'limit', 5 ) )}
{foreach $news as $item}
    {node_view_gui content_node=$item view='line'}
{/foreach}
{undef $news}

list returns direct children; tree goes down the subtree (limit it with depth). main_node_only avoids an object appearing twice when it has two locations below the same parent.

Filtering by class and by attribute

class_filter_type is include or exclude, with class_filter_array of class identifiers. attribute_filter is a list of conditions array( <field>, <operator>, <value> ), optionally starting with 'and' or 'or'; a field is <class>/<attribute> or a node property such as published, modified, section or name:

{def $upcoming = fetch( 'content', 'tree', hash(
        'parent_node_id', $node.node_id,
        'class_filter_type', 'include',
        'class_filter_array', array( 'exp_event' ),
        'attribute_filter', array( array( 'exp_event/start_date', '>=', currentdate() ) ),
        'sort_by', array( 'attribute', true(), 'exp_event/start_date' ),
        'limit', 10 ) )}

Operators and examples: Fetch filters and sorting. A template that compares with currentdate() and is view-cached keeps the time of caching; give such a page a short cache life (Caching for CMS developers).

Sorting

sort_by is array( <field>, <ascending> ), or a list of such pairs; fields include published, modified, name, priority, path, class_identifier and attribute (with the attribute as third element). To follow the order editors chose for a folder, pass the node's own order: 'sort_by', $node.sort_array.

Paging

The offset of a list comes from the view parameter (offset):

{def $limit = 10
     $total = fetch( 'content', 'list_count', hash( 'parent_node_id', $node.node_id ) )
     $page = fetch( 'content', 'list', hash( 'parent_node_id', $node.node_id,
                                              'offset', $view_parameters.offset,
                                              'limit', $limit,
                                              'sort_by', $node.sort_array ) )}
{foreach $page as $item}{node_view_gui content_node=$item view='line'}{/foreach}
{include name=navigator uri='design:navigator/google.tpl'
         page_uri=$node.url_alias item_count=$total
         view_parameters=$view_parameters item_limit=$limit}

The shipped navigators are in design/standard/templates/navigator/ (Pagination).

Rules for fast fetches

  • Always pass a limit on lists that can grow.
  • Filter by class in the fetch, not with {if} in the loop.
  • Avoid fetches inside loops over fetch results; fetch once, or use relations (The loop trap).
  • Use list_count for counts instead of counting a full list.
  • Put fetches that are the same on every page (menus, footers) in a cache block (Cache block).
  • Attribute filters on large trees are SQL joins; measure with the debug output's SQL list on a copy with real data.

When a fetch is not enough

When no fetch function answers your question, write one in your extension: a PHP method that returns data, declared in your module's function_definition.php, callable from every template (Fetch functions, A fetch function by hand). For complex filters, extended_attribute_filter lets a PHP class add SQL conditions; see settings/extendedattributefilter.ini.

Become an Exponential Partner

Partners share their information, provide funding, contribute back and develop the products with us, and that is how Exponential grows. A partner website and dashboard are planned for mid-2027: please become a partner today to speed up our growth rate and land new features faster.

Something wrong on this page? Report an error

Documentation license

This documentation is free documentation, licensed under the GNU Free Documentation License 1.3 or later.

Exponential Copyright © 1998-2026 Exponential Foundation and 7x