Using different templates for different tags

Continuing the discussion from Using custom summary partial inside custom list partial:

I am tagging my posts and would like to use different templates for different tags. My immediate use case is to show all posts tagged as “events” with customized views, and show all other posts (non-events) with a different view. To visually demonstrate this, I would like for the following paths

http://site/tags/
http://site/tags/events/
http://site/tags/<other-tags>/

These templates may look like so

└── tags
   ├── events
   │  ├── list.html
   │  ├── single.html
   │  └── summary.html
   ├── list.html
   │  ├── single.html
   └── summary.html

or like this (whichever works)

└── tags
   ├── events-list.html
   ├── events-single.html
   └── events-summary.html
   ├── other-list.html
   ├── other-single.html
   └── other-summary.html

How can I accomplish the above?

I understand your objective, but I encourage you to think carefully about your content model.

In my experience, an event is a type of content. For example:

content/
├── events/         # taxonomy term: meeting, party, performance
├── people/         # taxonomy term: actor, author, director
└── publications/   # taxonomy term: book, magazine, newspaper

With this model, you can use content view templates in conjunction with the .Render method.

yes @jmooring, your advice is good, but it is not easy for me to implement as it would require redoing a substantial part of the existing website. I would prefer to implement what I am currently seeking, but move to what you are suggesting only if my current aim is unimplementable.

Yeah, that one.

You can easily target a unique list template for:

  • https://example.org/tags
  • https://example.org/tags/event/

However:

  • To target a unique template for a single page, you would need to specify type and/or layout in the front matter of each content page.
  • To target a unique template for a content view using the .Render method, you would need specify type in the front matter of each content page.

Both of the above require something like:

+++
title = 'Post 1'
date = 2022-05-25T09:37:40-07:00
draft = false
tags = ['event']
type = 'event'
+++

Note the duplication of values – don’t do it.

ok, I have finally moved a couple of steps forward by doing the following in layouts/tags/list.html

{{- range (.Paginator 100).Pages.ByTitle }}
	{{ if eq .Type "event" }}
		{{ partial "event-summary.html" . }}
	{{ else }}
		{{- .Render "summary" }}
	{{- end }}
{{- end }}

note the use of a partial {{ if eq .Type "event" }} vs the .Render "summary" for non-event tags. The trick was to evaluate the equality within the range block. The only problem is, my posts that are tagged as events also have a dateStartOfEvent and I would like to sort the pages by this date rather than ByTitle. But I can’t evaluate the equality outside the range block because the value exists only inside pages.

If I add {{ printf "%#v" .Type }} outside the range block, and go to http://site/tags/events, it prints “tags”, and if I {{ printf "%#v" .Kind }} it prints “term”. What I really want is the value “events”, that is, the value of the “term” so that I can create the right .Paginator that can be sorted by dateStartOfEvent vs sorted ByTitle. This is the last hurdle in this quest as I’d like to be able to do

{{ if eq .Type "event" }}
    {{- range (.Paginator 100).Pages.ByParam "datestartofevent" }}
        {{ partial "event-summary.html" . }}
    {{- end }}	
{{ else }}
    {{- range (.Paginator 100).Pages.ByTitle }}
        {{- .Render "summary" }}
    {{- end }}
{{- end }}

oh, the result of the work so far can be seen on my staging website at

I did it !!! The following works (note, .Data.Term in the equality test)

{{ if eq .Data.Term "Events" }}
	{{- range (.Paginator 100).Pages.ByParam "datestartofevent" }}
		{{- partial "event-summary.html" . }}
	{{- end }}
{{- else }}
	{{- range (.Paginator 100).Pages.ByTitle }}
		{{- .Render "summary" }}
	{{- end }}
{{ end }}

This topic was automatically closed 2 days after the last reply. New replies are no longer allowed.