Single tweet nested partial

Goal: A page summarizing a collection of events; each event may contain a featured tweet. While looping through a data collection in a partial layout, output a tweet block based on the current tweetID.

Assumption: A shortcode cannot be used in a template (only in content files). So, attempting to make a partial that mimics a tweet shortcode with the TweetID passed from the parent partial.

Help! I’ve spend a lot of time researching and trying every combination I can think of. Does anyone know how to make this work? Thanks!

Relevant portions of files:

/data/events.yml

...
event:
  - name     : Huge Convention
    location : New York, NY
    desc     : Summarize experience at the huge gathering.
    tweet    : 1194607951958274049
  - name     : Amazing Conference
    location : Seattle, WA
    desc     : Summarize experience at the really huge gathering.
    tweet    : 917359331535966209
...

/layouts/events/list.html

...
{{ partial "event.html" (dict "future" true) }}

{{ partial "event.html" }}
...

/layouts/partials/event.html

{{ range $the_events }}
  ...
  {{/* tried to pass tweetID as single param */}}
  {{ partial "twitter.html" $event.tweet }} 
  {{/* also tried as named variable in dict */}}
  {{ partial "twitter.html" (dict "tweetid" $event.tweet) }}
  ...
{{ end }}

/layouts/partials/tweet-single.html
source: https://www.mgasch.com/post/shortcodes/

{{- $pc := .Page.Site.Config.Privacy.Twitter -}}
{{- if not $pc.Disable -}}
{{- if $pc.Simple -}}
{{ template "_internal/shortcodes/twitter_simple.html" . }}
{{- else -}}
{{- $url := printf "https://api.twitter.com/1/statuses/oembed.json?id=%v&dnt=%t" (index .Params 0) $pc.EnableDNT -}}
{{- $json := getJSON $url -}}
{{ $json.html | safeHTML }}
{{- end -}}
{{- end -}}

Hugo server error:

Rebuild failed:

Failed to render pages: render of "section" failed: 
"C:\Hugo\Sites\acme\web\themes\timer-hugo\layouts\events\list.html:6:82": 
execute of template failed: template: events/list.html:18:11: 
executing "events/list.html" at <partial "event.html" (dict "future" true)>: 
error calling partial: 
"C:\Hugo\Sites\acme\web\themes\timer-hugo\layouts\partials\event.html:6:82": 
execute of template failed: template: partials/event.html:49:23: 
executing "partials/event.html" at <partial "tweet-single.html" 
(dict "tweetid" $event.tweet)>: 
error calling partial: 
"C:\Hugo\Sites\acme\web\themes\timer-hugo\layouts\partials\tweet-single.html:6:82": 
execute of template failed: template: partials/tweet-single.html:6:82: 
executing "partials/tweet-single.html" at <index .Params 0>: 
error calling index: index of untyped nil

Where do you define, that $event should have the item in the range?

{{{ range $index, $event := $the_events }}

$index counts up from 0, $event contains your subitem.

$the_events should probably be defined somewhere too with something like

{{ $the_events := $.Site.Data.events }}

The docs are here:

your indexed range:

how to retrieve data:

You are close. So when you pass a dict to a partial like you’re doing here:

{{ partial "twitter.html" (dict "tweetid" $event.tweet) }}

Do access the value of the tweetid key, instead of doing this:

index .Params 0

Do this:

.tweetid

For a docs example see https://gohugo.io/functions/dict/#example-using-dict-to-pass-multiple-values-to-a-partial

1 Like

Thanks, @zwbetz.

The (index .Params 0) line was in the original I cited. So that is why I tried passing a single parameter.

I also changed the partial include to the dict syntax and then accessing the tweetid with every combination I can think of with and without parens, dots, dollar, scratch, etc.:
.tweetid, $tweetid, $.tweetid, (.tweetid), ($tweetid), ($.tweetid), etc.

Nothing results in a successful site build.

So, I just commented out all of the contents of the tweet-single.html file to see if I could echo the ID:
<p>The tweet ID is: {{ .tweetid }}</p>

It does indeed output the correct ID numbers from the yml file. So .tweetid is correct as you suggested.

Perhaps there is some conflict in another part of the tweet-single.html script I used that works as a shortcode but not as a partial?

Thanks, @davidsneighbour. Those aspects are all working fine. I omitted the range for brevity. And yes, my tweet id is in the array. The data outputs correctly as long as I omit the twitter section. The beginning of event.html looks like:

{{ $scratch := newScratch }}
{{ $scratch.Set "when" "Past" }}
{{ if .future }}
    {{ $scratch.Set "when" "Upcoming" }}
{{ end }}

{{ $the_events := slice }}

    {{ if .future }}
        {{ range site.Data.events.item }}
            {{ if ge (time .enddate).Unix now.Unix }}
                {{ $the_events = $the_events | append . }}
            {{ end }}
        {{ end }}
    {{ else }}
        {{ range site.Data.events.item }}
            {{ if lt (time .enddate).Unix now.Unix }}
                {{ $the_events = $the_events | append . }}
            {{ end }}
        {{ end }}
    {{ end }}

Credit to @zwbetz for the slice solution. Time function in range condition

Maybe the problem is the template call on line 6. It references a shortcode template and this is being adapted for use as a partial. Not sure where to find _internal files. Will research this angle.

Possibly related: https://github.com/gohugoio/hugo/issues/6382

The new question is: Has anyone built a partial layout to display a tweet?

Partial solution works except when: .Site.Params.privacy.twitter.simple:true. My problems were a combination of variable context and privacy settings in shortcode.

config.toml: Added global GDPR settings per https://gohugo.io/about/hugo-and-gdpr/. Prepended params. to each item:

# GDPR settings per https://gohugo.io/about/hugo-and-gdpr/
[params.privacy]
    [params.privacy.disqus]
        disable = false
    [params.privacy.googleAnalytics]
        anonymizeIP = false
        disable = false
        respectDoNotTrack = false
        useSessionStorage = false
    [params.privacy.instagram]
        disable = false
        simple = false
    [params.privacy.twitter]
        disable = false
        enableDNT = false
        simple = false
    [params.privacy.vimeo]
        disable = false
        simple = false
    [params.privacy.youtube]
        disable = false
        rivacyEnhanced = false

list.html: Needed to include site params in call to event partial using dict.

{{ partial "event.html" (dict "future" true "priv_tw" .Site.Params.privacy.twitter) }}

{{ partial "event.html" (dict "future" false "priv_tw" .Site.Params.privacy.twitter) }}

event.html: Included params in call to nested tweet partial.

{{ if $event.tweet }}
    {{ partial "tweet-single.html" (dict "privacy_tw" $.priv_tw "tweet_id" $event.tweet ) }}
 {{ end }}

tweet-single.html: Modified source from https://www.mgasch.com/post/shortcodes/ shortcode for use in partial. Still need to figure out .Site.Params.privacy.simple:true scenario.

{{- $pr := .privacy_tw -}}
{{- if not $pr.disable -}}
    {{- if $pr.simple -}}
        {{/* build error:
             execute of template failed: template: _internal/shortcodes/twitter_simple.html:4:11: executing "_internal/shortcodes/twitter_simple.html" at <.Get>: Get is not a method but has arguments

            {{ template "_internal/shortcodes/twitter_simple.html" . }}
        */}}
        
        <p>If .Site.Params.privacy.simple=true, need alternative to _internal/shortcodes/twitter_simple.html.</p>
    {{- else -}}
        {{- $tw_qry_str := print "&id=" .tweet_id "&dnt=" $pr.enablednt -}}
        {{/*<p>Twitter query string: {{ $tw_str }}</p>*/}}
        {{- $url := print "https://api.twitter.com/1/statuses/oembed.json?hide_thread=1" $tw_qry_str -}}
        {{/*<p>Twitter API URL: {{ $url }}</p>*/}}
        
        {{- $json := getJSON $url -}}
        {{ $json.html | safeHTML }}
        
    {{- end -}}
{{- end -}}