On Thu, Nov 27, 2025 at 06:27:23PM +0100, Kamil Jonca wrote:
> I have quite complicated sieve script. 
> I found that last package version does not set variable 
> ==============
> require [ "comparator-i;ascii-numeric","relational" 
> ,"vnd.dovecot.execute","vnd.dovecot.pipe","vnd.dovecot.filter","fileinto" 
> ,"regex" ,"variables" ,"body" ,"copy" ,"date" ,"imap4flags" 
> ,"vnd.dovecot.debug" ,"editheader","index","encoded-character"]; 
> [....]
> 
> if header :regex "list-id" "<?([^<>]+)>?[[:space:]]*$"                  
> {
>       set "KJ_list_id" "${1}";
>       debug_log "list: ${KJ_list_id}";
> }
> elsif header :regex "X-Mailing-List" "<?([^<>]+)?>.*"
> {
>       set "KJ_list_id" "${1}";
>       debug_log "list: ${KJ_list_id}";
> }
> debug_log "list(uncond): ${KJ_list_id}";
> 
> [...]
> 
> then 
> =========
> %sieve-filter -e -W -D -C -v ~/.dovecot.sieve z/1
> [...]
> info: filtering: [Fri, 28 Nov 2025 00:45:39 +1100; 10716 bytes] '[pfx] Re: 
> Reminder to drop TLSA RRs m...'.
> sieve-filter: Debug: sieve: Started running script '_file/.dovecot'
> info: DEBUG: list(uncond): .
> [...]
> =========
> so variable is not set ...
> 
> 
> This message with dovecot-sieve: 1:2.4.1+dfsg1-9 
> =============
> info: filtering: [Fri, 28 Nov 2025 00:45:39 +1100; 10716 bytes] '[pfx] Re: 
> Reminder to drop TLSA RRs m...'.
> sieve-filter: Debug: sieve: Started running script '_file/.dovecot'
> info: DEBUG: list: postfix-users.postfix.org.
> info: DEBUG: list(uncond): postfix-users.postfix.org.
> =============

Dovecot upstream switched to a different regex engine with version
2.4.2.  It now uses libpcre2, which may have subtle behavior differences
from the previous regex engine.  Indeed I think that's the issue here.

With your list-id regex and perl, we don't match the list ID:

$ echo 'List-Id: "For discussions about using Postfix: questions, problem 
reports, or feature requests. Open subscription, unmoderated, posting by 
members only." <postfix-users.postfix.org>' | perl -n -e 
'm/^List-Id.*<?([^<>]+)>?[[:space:]]*$/ && print("matched [$1]\n");'
matched [
]

If we modify the regex slightly, it works both with perl and dovecot/pcre2:

$ echo 'List-Id: "For discussions about using Postfix: questions, problem 
reports, or feature requests. Open subscription, unmoderated, posting by 
members only." <postfix-users.postfix.org>' | perl -n -e 
'm/^List-Id.*<([^<>]+)>?[[:space:]]*$/ && print("matched [$1]\n");' 
matched [postfix-users.postfix.org]

$ cat test.sieve 
require [ "comparator-i;ascii-numeric","relational" ,"fileinto" ,"regex" 
,"variables" ,"body" ,"copy" ,"date" ,"imap4flags" ,"vnd.dovecot.debug" 
,"index","encoded-character"];

if header :regex "list-id" "<([^<>]+)>?[[:space:]]*$"
{
        set "KJ_list_id" "${1}";
        debug_log "list: ${KJ_list_id}";
}
elsif header :regex "X-Mailing-List" "<?([^<>]+)?>.*"
{
        set "KJ_list_id" "${1}";
        debug_log "list: ${KJ_list_id}";
}
debug_log "list(uncond): ${KJ_list_id}";
$ sieve-test test.sieve testheaders.txt
info: DEBUG: list: postfix-users.postfix.org.
info: DEBUG: list(uncond): postfix-users.postfix.org.

Performed actions:

  (none)

Implicit keep:

 * store message in folder: INBOX

sieve-test: Info: final result: success

So I think, given the consistent behavior between perl and pcre2, that
this change in behavior should be considered correct and that you should
adjust your sieve script accordingly.

noah

> List-Id: "For discussions about using Postfix: questions, problem reports,
>  or feature requests. Open subscription, unmoderated,
>  posting by members only." <postfix-users.postfix.org>

Reply via email to