1 /**
2  * @file
3  * Handle mailing lists
4  *
5  * @authors
6  * Copyright (C) 2020 Richard Russon <rich@flatcap.org>
7  *
8  * @copyright
9  * This program is free software: you can redistribute it and/or modify it under
10  * the terms of the GNU General Public License as published by the Free Software
11  * Foundation, either version 2 of the License, or (at your option) any later
12  * version.
13  *
14  * This program is distributed in the hope that it will be useful, but WITHOUT
15  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16  * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
17  * details.
18  *
19  * You should have received a copy of the GNU General Public License along with
20  * this program.  If not, see <http://www.gnu.org/licenses/>.
21  */
22 
23 /**
24  * @page neo_maillist Handle mailing lists
25  *
26  * Handle mailing lists
27  */
28 
29 #include "config.h"
30 #include <stdbool.h>
31 #include <stdio.h>
32 #include "mutt/lib.h"
33 #include "address/lib.h"
34 #include "email/lib.h"
35 #include "maillist.h"
36 #include "muttlib.h"
37 #include "sort.h"
38 
39 /**
40  * mutt_is_mail_list - Is this the email address of a mailing list? - Implements ::addr_predicate_t - @ingroup addr_predicate_api
41  * @param addr Address to test
42  * @retval true It's a mailing list
43  */
mutt_is_mail_list(const struct Address * addr)44 bool mutt_is_mail_list(const struct Address *addr)
45 {
46   if (!mutt_regexlist_match(&UnMailLists, addr->mailbox))
47     return mutt_regexlist_match(&MailLists, addr->mailbox);
48   return false;
49 }
50 
51 /**
52  * mutt_is_subscribed_list - Is this the email address of a user-subscribed mailing list? - Implements ::addr_predicate_t - @ingroup addr_predicate_api
53  * @param addr Address to test
54  * @retval true It's a subscribed mailing list
55  */
mutt_is_subscribed_list(const struct Address * addr)56 bool mutt_is_subscribed_list(const struct Address *addr)
57 {
58   if (!mutt_regexlist_match(&UnMailLists, addr->mailbox) &&
59       !mutt_regexlist_match(&UnSubscribedLists, addr->mailbox))
60   {
61     return mutt_regexlist_match(&SubscribedLists, addr->mailbox);
62   }
63   return false;
64 }
65 
66 /**
67  * check_for_mailing_list - Search list of addresses for a mailing list
68  * @param al      AddressList to search
69  * @param pfx     Prefix string
70  * @param buf     Buffer to store results
71  * @param buflen  Buffer length
72  * @retval 1 Mailing list found
73  * @retval 0 No list found
74  *
75  * Search for a mailing list in the list of addresses pointed to by addr.
76  * If one is found, print pfx and the name of the list into buf.
77  */
check_for_mailing_list(struct AddressList * al,const char * pfx,char * buf,int buflen)78 bool check_for_mailing_list(struct AddressList *al, const char *pfx, char *buf, int buflen)
79 {
80   struct Address *a = NULL;
81   TAILQ_FOREACH(a, al, entries)
82   {
83     if (mutt_is_subscribed_list(a))
84     {
85       if (pfx && buf && buflen)
86         snprintf(buf, buflen, "%s%s", pfx, mutt_get_name(a));
87       return true;
88     }
89   }
90   return false;
91 }
92 
93 /**
94  * check_for_mailing_list_addr - Check an address list for a mailing list
95  * @param al     AddressList
96  * @param buf    Buffer for the result
97  * @param buflen Length of buffer
98  * @retval true Mailing list found
99  *
100  * If one is found, print the address of the list into buf.
101  */
check_for_mailing_list_addr(struct AddressList * al,char * buf,int buflen)102 bool check_for_mailing_list_addr(struct AddressList *al, char *buf, int buflen)
103 {
104   struct Address *a = NULL;
105   TAILQ_FOREACH(a, al, entries)
106   {
107     if (mutt_is_subscribed_list(a))
108     {
109       if (buf && buflen)
110         snprintf(buf, buflen, "%s", a->mailbox);
111       return true;
112     }
113   }
114   return false;
115 }
116 
117 /**
118  * first_mailing_list - Get the first mailing list in the list of addresses
119  * @param buf    Buffer for the result
120  * @param buflen Length of buffer
121  * @param al     AddressList
122  * @retval true A mailing list was found
123  */
first_mailing_list(char * buf,size_t buflen,struct AddressList * al)124 bool first_mailing_list(char *buf, size_t buflen, struct AddressList *al)
125 {
126   struct Address *a = NULL;
127   TAILQ_FOREACH(a, al, entries)
128   {
129     if (mutt_is_subscribed_list(a))
130     {
131       mutt_save_path(buf, buflen, a);
132       return true;
133     }
134   }
135   return false;
136 }
137