Skip to content
Permalink

Comparing changes

This is a direct comparison between two commits made in this repository or its related repositories. View the default comparison for this range or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: cyrusimap/cyrus-imapd
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: c22fc98039f09a8ba9e14a1b17b567feb3f88237
Choose a base ref
..
head repository: cyrusimap/cyrus-imapd
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: adcd55cfdeb4b45d2e8b687a091d827c6f8f4af1
Choose a head ref
Showing with 86 additions and 35 deletions.
  1. +1 −0 cassandane/Cassandane/Cyrus/JMAPSieve.pm
  2. +82 −33 cassandane/tiny-tests/JMAPSieve/sieve-test-extensive
  3. +3 −2 imap/jmap_sieve.c
1 change: 1 addition & 0 deletions cassandane/Cassandane/Cyrus/JMAPSieve.pm
Original file line number Diff line number Diff line change
@@ -80,6 +80,7 @@ sub new
}

$config->set(caldav_realm => 'Cassandane',
conversations_counted_flags => "\\Draft \\Flagged \$IsMailingList \$IsNotification \$HasAttachment \$muted",
conversations => 'yes',
httpmodules => 'carddav caldav jmap',
httpallowcompress => 'no',
115 changes: 82 additions & 33 deletions cassandane/tiny-tests/JMAPSieve/sieve-test-extensive
Original file line number Diff line number Diff line change
@@ -80,67 +80,98 @@ add_sieve_tests(
[ ['keep', {}, [] ] ],
);

sub add_sieve_tests {
my (@tests) = @_;
sub test_sieve_test_extensive_some_in_thread_have_keyword
:min_version_3_3 :JMAPExtensions
{
my ($self) = @_;

my $leftover = @tests % 3;
# Create two messages, where the first is muted and the second is in
# the same conversation
my $mid = '<cassandane@example.com>';

if ($leftover) {
die "We expected multiple sets of 3 test specifications, but after parsing we'd have $leftover extra items... something is wrong!\n";
}
my (undef, $email1) = $self->new_email_blob({
'keywords' => { '$muted' => JSON::true },
'header:Message-Id' => $mid,
});

my ($email2_blob_id, $email2) = $self->new_email_blob({
'header:inReplyTo' => $mid,
'header:references' => $mid,
});

$self->assert_str_equals($email1->{threadId}, $email2->{threadId});

my $sieve_blob_id = $self->new_sieve_blob(
'if jmapquery "{\"someInThreadHaveKeyword\":\"$muted\"}" {
fileinto "muted";
}',
);

$self->run_sieve_test(
$sieve_blob_id,
$email2_blob_id,
[ ['fileinto', {}, ['muted'] ] ],
);
}

sub add_sieve_tests {
my (@tests) = @_;

while (@tests) {
add_sieve_test(
my ($name, $sieve, $expect) = (
shift @tests,
shift @tests,
shift @tests,
);

if (! $expect) {
die "Expected at least 3 arguments, but didn't get it. Bad test spec?! "
. Dumper({
name => $name,
sieve => $sieve,
});
}

my $opts;

if (@tests && ref $tests[0] eq 'HASH') {
$opts = shift @tests;
}

add_sieve_test($name, $sieve, $expect, $opts);
}
}

sub add_sieve_test {
my ($name, $sieve, $expect, $variables) = @_;
my ($name, $sieve, $expect, $opts) = @_;

unless ($name =~ /^[a-zA-Z][a-zA-Z0-9_]+$/) {
die "Test name '$name' invalid. Must look like a perl subroutine name (start with a letter, a-zA-Z0-9_ only after that...\n";
}

Sub::Install::install_sub({
code => sub :min_version_3_3 :JMAPExtensions {
shift->_do_test($sieve, $expect, $variables);
shift->_do_test($sieve, $expect, $opts);
},
as => "test_sieve_test_extensive_$name",
});
}

sub _do_test {
my ($self, $sieve, $expect, $variables) = @_;
my ($self, $sieve, $expect, $opts) = @_;

my $variables = $opts->{variables};
my $email_set_params = $opts->{email_set_params};

my $sieve_blob_id = $self->new_sieve_blob($sieve);
my $email_blob_id = $self->new_email_blob;
my $email_blob_id = $self->new_email_blob($email_set_params);

my $res = $self->run_sieve_test(
$self->run_sieve_test(
$sieve_blob_id,
$email_blob_id,
$expect,
$variables,
);

eval {
$self->assert_deep_equals(
$expect,
$res->[0][1]{completed}{$email_blob_id},
);
};

if ($@) {
my $err = $@;

warn "Wanted: " . Dumper($expect);
warn "Got: " . Dumper($res->[0][1]{completed}{$email_blob_id});

# Rethrow for Test::Unit's sake
die $@;
}
}

sub new_sieve_blob {
@@ -181,7 +212,7 @@ EOF
}

sub new_email_blob {
my ($self) = @_;
my ($self, $email_set_params) = @_;

my $jmap = $self->{jmap};

@@ -200,7 +231,8 @@ sub new_email_blob {
to => [ { name => "Bugs Bunny", email => "bugs\@acme.local" }, ],
subject => "Memo",
textBody => [{ partId => '1' }],
bodyValues => { '1' => { value => "Whoa!" }}
bodyValues => { '1' => { value => "Whoa!" }},
( $email_set_params ? ( %$email_set_params ) : () ),
};

$res = $jmap->CallMethods([
@@ -210,11 +242,11 @@ sub new_email_blob {
my $email_blob_id = $res->[0][1]{created}{"1"}{blobId};
$self->assert_not_null($email_blob_id);

return $email_blob_id;
return wantarray ? ($email_blob_id, $res->[0][1]{created}{"1"}) : $email_blob_id;
}

sub run_sieve_test {
my ($self, $sieve_blob_id, $email_blob_id, $variables) = @_;
my ($self, $sieve_blob_id, $email_blob_id, $expect, $variables) = @_;

my $jmap = $self->{jmap};

@@ -232,5 +264,22 @@ sub run_sieve_test {
$self->assert_not_null($res->[0][1]{completed});
$self->assert_null($res->[0][1]{notCompleted});

eval {
$self->assert_deep_equals(
$expect,
$res->[0][1]{completed}{$email_blob_id},
);
};

if ($@) {
my $err = $@;

warn "Wanted: " . Dumper($expect);
warn "Got: " . Dumper($res->[0][1]{completed}{$email_blob_id});

# Rethrow for Test::Unit's sake
die $@;
}

return $res;
}
5 changes: 3 additions & 2 deletions imap/jmap_sieve.c
Original file line number Diff line number Diff line change
@@ -2068,7 +2068,7 @@ static int jmap_sieve_test(struct jmap_req *req)
if (JNOTNULL(variables) && json_is_object(variables)) {
jmap_parser_push(&parser, "variables");

construct_hash_table(&vars, 64, 0);
construct_hash_table(&vars, 16, 0);

const char *key;
json_t *value;
@@ -2166,6 +2166,8 @@ static int jmap_sieve_test(struct jmap_req *req)
goto done;
}

interp_ctx.cstate = req->cstate;

/* create interpreter */
interp = sieve_interp_alloc(&interp_ctx);
sieve_register_header(interp, getheader);
@@ -2257,7 +2259,6 @@ static int jmap_sieve_test(struct jmap_req *req)
}
}

if (interp_ctx.cstate) conversations_commit(&interp_ctx.cstate);
if (interp_ctx.carddavdb) carddav_close(interp_ctx.carddavdb);

/* Build response */