How do I exclude posts based on any one of multiple tags?

This is a working version of the opposite of what I’m looking for:

{{ $display_posts := (((.Site.GetPage "section" "/posts").Pages).ByDate.Reverse) }}
      {{ range $post := (where $display_posts "Params.tags" "intersect" (slice "Rstats" "rstats" "python")) }}

This successfully loads posts from my posts folder and then iterates over each of them where at least one of these tags appears, excluding posts where there are no tags matching those in slice.

However, I haven’t been able to find a method where I write a slice of tags to exclude. I want to be able to exclude posts from this view based on if any of the posts tags matchs any one of the tags in the slice.

replacing intersect with "in" and "not in" both lead to no posts showing up. "!=" has the same effect.

How do I write a filter to exclude a post based on multiple tags?

If more context is needed, here is the repo, with the relevant work being done on the exclude-by-tag branch.

There might be a simpler solution, but symdiff could probably help:

I think with ne in your sample code you might get faster there, just not sure where:

1 Like

Thanks, I’ve had a look, but I’m not sure I’m getting how symdiff could help. Could you please expand a bit on why you think that might work?

collection 1: [all, the, tags, that, you, have, plus, the, three, tag1, tag2, tag3, to, remove]
collection 2: [tag1, tag2, tag3]

I would expect symdiff to return: [all, the, tags, that, you, have, plus, the, three, to, remove]

And now writing it down it doesn’t make any more sense to me :wink:

Let’s go another way with your task - break it into two parts

  1. range through all posts
  2. inside of the range check that none of the three tags is in the post
{{ $display_posts := (((.Site.GetPage "section" "/posts").Pages).ByDate.Reverse) }}
{{ range $post := $display_posts }}
{{ if ((not in .Params.tags "tag1") and (not in .Params.tags "tag2"))  }}
something
{{ end }}
{{ end }}

Something like this… I am not sure if the syntax is correct.

1 Like

Thanks. I’m pretty sure the syntax is incorrect:

execute of template failed: template: _default/blog.html:11:14: executing "content" at <not>: wrong number of args for not: want 1 got 3
{{ if 
(
    (not 
        (in .Params.tags "tag1") 
    )
and 
    (not 
        (in .Params.tags "tag2")
    ) 
)
}}

brackets :roll_eyes:

{{ if ((not (in .Params.tags "tag1")) and (not (in .Params.tags "tag2")))}}
1 Like

Thanks for your continued help, I’m still not sure that’s right though. It’s appearing on my machine as if the second conditional doesn’t have an effect. For instance if I use:

{{ if ((not (in .Params.tags "question")) and (not (in .Params.tags "help")))}}

It will remove the post with the tag question but not the one tagged help. However, if I use the reverse:

{{ if ((not (in .Params.tags "help")) and (not (in .Params.tags "question")))}}

I remove all the posts with help, but the question reappears.

Is it possible that apply might be able to be fed a conditional check on a slice?

It’s most probably “just” some logic confusion.

{{ 
if (
    not (                                     <-- not
        (in .Params.tags "question")          <-- tag question
        or                                    <-- OR
        (in .Params.tags "help")              <-- tag help
    )
)
}}

so:

{{ if (not ((in .Params.tags "question") or (in .Params.tags "help")))}}

It would really help if you could put a public repo online that we can use to play around. I am playing with Schroedingers cat here and though I read a day ago that they might have found a solution to have it being alive at all times I don’t have the mental capacity to confirm that :crazy_face:

I did not use apply yet in my projects… so I got no idea about that without samples.

I am pretty sure Golang or Hugo has some kind of “string not in this array of strings” construct.

1 Like

Haha, that’s a lucky cat. I actually thought I did put the public repo up in my first post? Here it is again:

It appears to me that it’s public, but let me know if from your side it isn’t :slight_smile:

You know, the script kiddie solution would be the following:

{{ $display_posts := (((.Site.GetPage "section" "/posts").Pages).ByDate.Reverse) }}
{{ range $post := $display_posts }}
{{ if in .Params.tags "tag1" }}<!-- nah //-->
{{ else if in .Params.tags "tag2" }}<!-- nah either //-->
{{ else }}
THIS IS WHERE NEITHER TAG IS USED
{{ end }}
{{ end }}

I’ll be checking your repo now. Partial blindness on my behalf.

1 Like

Not sure why it’s from last year :smiley:

1 Like

So that approach does work, but I’d really like to know if there is an alternative, so I’m going to leave this open for a bit to see if anyone else has an idea. If I don’t get a response tomorrow though, I’ll close this off with that solution :slight_smile:

It’s so dirty. Let’s try to find a more elegant way.

1 Like