Inconsistent behavoir & absence of documentation for `title` and `label` property for the page-template

Continuing the discussion from Duplicating & changing title still possible eventhough option is set to disabled:

I just found something out about the page-bleuprint’s title and label property when trying out the page-template mechanism which does not seem to be documented!

first of all, every page-blueprint is interpreted as an available page-template which was surprising as I thought those needed to be registered in the template plugin hook? (but I suspect those with no actual page-template file will fallback to the default.php template).

Second; The title property is apparently used for the actual page-title with a fallback to the label property, while the label property is actually used as ‘page-template/blueprint name’ which is showed whe creating a new page. The label property has the title property as fallback, which is a verry curious choice to be honest. Since the title property allows query language syntax, but the label doesn’t.

So if I want to create a new page, there is a bunch of options (one for every page-bleuprint) with the label {{page.title}}. I think it would be much better to use the syntax {plugin_namespace}/{file_name} or something simular as fallback instead. (as there is now simply no way to find the difference between {{page.title}} and {{page.title}} :stuck_out_tongue:)

Upon this discovery there are two questions for me:

  1. How to exclude a page-blueprint to be interpreted as an avialable page-template?
  2. How does this work with ‘page models’, I mean in the documenation it is mentioned you need to create an php-class extending the Page class, with a filename corresponding the page-template filename. Does this mean one can skip the page-template and simply use a page-blueprint file instead?

No, only blueprints that you want to provide via plugin need to be registered-

The blueprint title property is used for display in the page create dialog, not for the page title. If a page has no title, Kirby falls back to the folder name. A blueprint has no label property (tabs and fields have a label property)

I don’t understand this question

Blueprint is a yaml file that defines the fields etc. for the Panel.
Template is a php file with the HTML that is rendered on the frontend.
Two different things.

That is what I thought as well, but currently I have only one template registered. And multiple page-blueprints. Eventhough I did not register additional page-templates I can still choose from every single page-template backed by the defined page-blueprints when I want to add a new page. (I do everything through plugins, to keep the original Kirby installation intact btw.)

I have to say though, that I put the site as parent for the pages section, if that should make a difference.

I linked a specific post in the discussion. As seen there both the title and label yields the same visual result, eventhough it is undocumented.

The result is not the same, it shows for example Pages/album instead of Album when you use title: Album? So the fallback is to the blueprints foldername/blueprintname. So to prevent the fallback name, you have to use the title like starting with a lower-case t

I just tested that, and it seems to check out. So label is no fallback. That still leaves the page-template addition problem. How to prevent that?

I don’t really understand the problem. What is your use case?

:smiley: none? I simply noticed that page-bleuprints were added as page-templates without eplicitly registering them. And I don’t want that because some page-templates are either ‘singletons’ or plugin-specific templates.

What does that mean?

Plugin-specific blueprint can be overridden by putting a blueprint with the same name into /site/blueprints, so that’s a feature.

And there is no way to not auto-register such blueprints apart from simply removing them if you don’t want or need them.

oke, let put some sample code, because I don’t think its the ‘auto-register’ feature which is doing something.


App::plugin('my/plugin', [
    'templates' => buildArray(__DIR__ . '/templates'),
    'blueprints' => buildArray(__DIR__ . '/blueprints')

// Internal utility

function buildArray(string $dir)
    $a = array();
    return _buildArray($dir, '', $a);

function _buildArray(string $dir, string $prefix = '', array &$arr)
    foreach (scandir($dir) as $file) {
        $bn = pathinfo($file);

        if ($bn['basename'] !== '.' && $bn['basename'] !== '..') {
            $ap = $dir . DIRECTORY_SEPARATOR . $file;

            if (is_dir($ap)) {
                _buildArray($ap, $prefix . $bn['basename'] . '/', $arr);
            } else $arr[$prefix . $bn['filename']] = $ap;
    return $arr;

The above code is all I currently have which is doing something with bleuprints & templates. Eventhough there is just 1 template in existence. I can still choose the 3 based on the blueprint files (again, eventhough I do not register any templates based on those blueprint files!).

Does that refer to ‘auto-registering’? or is there something I am missing here?

Choose where? In the create page dialog? But what you choose in the create page dialog is the blueprint, not the template (event though it is called template (as in “intendedTemplate”). The name of the blueprint you choose when creating a new page is responsible for your content text file name which in turn defines which template is used when it gets to rendering a page (either a template with that name or the default template if the intended template does not exist).

So if I’m not mistaken this is probably a misunderstanding due to the label of the select field in the page create dialog?

:man_facepalming: names are always my nemesis… Yes that has been the misunderstanding apparently

So how does one decide which (actual) template should be used for a new page? I mean, is that customizable by a panel user? Or better put, is there a way to change it afterwards if the content is exactly the same? (e.g. make a general-post into a review-post for example. Content is exactly the same, but it is displayed a little differently)

You decide what template is used by choosing the blueprint/template with the same name as the template you want to use for rendering:


When you create a page, you choose album.yml as blueprint/template in the select field in the page create dialog.

The page is created with content txt file album.txt

If album.php template exists, that will be used to render file.

So if I want to create multiple pages based on the same blueprint (eventhough the names do not match). Does that mean it will choose the ‘default’ template, just because the page-name (and therefore the file-name) do not match?

You can create as many pages as you like based on the same blueprint. If you have a parent blog page, for example, all your blog page children will probably use the same blueprint blog-article (of course, you could also have different types as subpages, but that’s another story).

Have a look at the Starterkit as example. All subpages of notes use the note.yml blueprint, all subpages of photography use the album.yml blueprint (and therefore all have a note.txt/album.txt` content file).

The subpages in notes are rendered with the note.php template, the subpages in photography with the album.php template.