afewmail / afew Goto Github PK
View Code? Open in Web Editor NEWan initial tagging script for notmuch mail
License: ISC License
an initial tagging script for notmuch mail
License: ISC License
james@francium:~/.local/bin$ ./afew --update-reference
Traceback (most recent call last):
File "./afew", line 9, in
load_entry_point('afew==0.0.0', 'console_scripts', 'afew')()
File "/home/james/.local/lib/python2.7/site-packages/afew-0.0.0-py2.7.egg/afew/commands.py", line 187, in main
with Database() as database:
AttributeError: exit
I feel it would be more comfortable if add_tags() accepted a list instead of a variable number of tags.
But since python doesn't support method overloading, I refrain from adding a add_tag_list() method.
Whud do you think?
Hi
I started using afew and it is REALLY nice. But I still have a few question on how to change some rules (mailing list identification). I guess the "issues: section is not the best place to ask.
Is there a mailing list I could use to ask ask or should I mail you directly?
Thanks,
Rainer
The dbacl documentation warns against this:
The input text for learning is assumed to be unstructured plain text by default. This is not suitable for learning email, because email contains various transport encodings and formatting instructions which can reduce classification effectiveness. You must use the -T switch in that case so that dbacl knows it should perform decoding and filtering of MIME and HTML as appropriate. Apropriate switch values are "-T email" for RFC2822 email input[…].
Luckily it's a simple fix, unluckily you should probably regenerate your categorizations after this.
So far one has to specify a non-standard path to the notmuch db on the command line. Since the notmuch config knows where to find its db, I think it would be nice if afew got that info from there (especially since it's one you would otherwise have to pass on every single execution of afew).
The corresponding config:
[HeaderMatchingFilter.0]
message = Tag github notifications...
header = References
pattern = ^\<(?P<orga>[a-zA-Z0-9-_]+)\/(?P<repo>[a-zA-Z0-9-_]+)\/(?P<type>[a-zA-Z0-9-_]+)\/(?P<number>\d+)\@github\.com\>$
tags = +github;+{repo};+{type}
I only add tags for repo and type. If you also like tags for the organization and/or the issue number add "+{orga}" and/or "+{number}" as you like.
One issue remains: type is "issues" or "pull" - is there a solution to either set both to singular or plural? (issue/pull or issues/pulls)
iff afew is meant to be an initial tagging script for notmuch (and I feel like it is meant to be, mainly due to it handling sent mail, killed threads and spam) vs an addon project with classification magic, I think it needs to be able to do some initial tagging ;) i.e. tag new mails according to arbitrary rules. Basically is needs to wrap the functionality of 'notmuch tag'.
I guess people will want to be able to do things like
$ notmuch tag +office +inbox -new -- tag new and to:[email protected]
$ notmuch tag +private +inbox -new -- tag new and to:[email protected]
We probably want to read in a file of tagging rules and pipe them through notmuch - format unknown as of yet ;)
dtk
docs/source/extending.rst
suggests that custom filters in ~/.config/afew
should start with:
from afew.Filter import Filter, register_filter
But there is no afew.Filter
module nor is there a register_filter
function defined anywhere.
afew fails to run because it misses the package "subprocess32". As I understand [1] it's a port of the python-3.2 "subprocess" module to python 2.*. When I run with python3.2 this IMHO should not needed. Also the sources only import subprocess.
Could this requirement be made optional in setup.py? Or should that be simply patched out when installing for python3.2? I removed the subprocess32-line from "requires.txt" and at least it does not abort anymore with
pkg_resources.DistributionNotFound: subprocess32
Hi, Thanks for afew, it's great.
I'm having some issues with the MailMover class. I may be missing something but if so then I've not been able to see what...
The directory matching test on lines 65 and 66:
to_move_fnames = [name for name in all_message_fnames
if maildir in name]
Will not match directories in the config which are surrounded by quotes. As IMAP folders can have spaces in their names they wouldn't be able to match in this case.
Also, in cases where the destination is a sub-folder of the source, as is the case in my Maildir where all folders are children of INBOX, files in the destination folder will also pass this test, making the copy fail as it tries to copy the file over itself:
Traceback (most recent call last):
File "/usr/local/bin/afew", line 9, in <module>
load_entry_point('afew==0.0.0', 'console_scripts', 'afew')()
File "/usr/local/lib/python2.7/dist-packages/afew-0.0.0-py2.7.egg/afew/commands.py", line 203, in main
inner_main(options, database, query_string)
File "/usr/local/lib/python2.7/dist-packages/afew-0.0.0-py2.7.egg/afew/main.py", line 83, in main
mover.move(maildir, rules)
File "/usr/local/lib/python2.7/dist-packages/afew-0.0.0-py2.7.egg/afew/MailMover.py", line 76, in move
shutil.copy2(fname, destination)
File "/usr/lib/python2.7/shutil.py", line 130, in copy2
copyfile(src, dst)
File "/usr/lib/python2.7/shutil.py", line 69, in copyfile
raise Error("`%s` and `%s` are the same file" % (src, dst))
shutil.Error: `/home/tolan/mail/ops/INBOX/.Foo/cur/1410471077.4046_9.orbit,U=1452:2,S` and `/home/tolan/mail/ops/INBOX/.Foo/cur/1410471077.4046_9.orbit,U=1452:2,S` are the same file
I think the concept of (plug'n'play) filters to add tagging functionality is pretty brilliant. I have to admit, though: I didn't get it till I looked at the code (from that point on it was perfectly clear - no idea how one could ever do it differently ;)).
So I think it either needs explanation in the documentation (so the user may understand why --tag will 'run the tag filter' and what the filter classes are that can be used with --enable-filters) or the current documentation should avoid mentioning the concept of tag filters.
When running afew --tag --new -vv I am getting the following error output:
DEBUG:root:executing [u'dbacl', u'-c',
u'/home/bb/.local/share/afew/categories/reference_category', u'-c',
u'/home/bb/.local/share/afew/categories/spam', u'-n']
Traceback (most recent call last):
File "/home/bb/.local/bin/afew", line 189, in
main(options, query_string)
File "/home/bb/.local/lib/python2.7/site-packages/afew/main.py",
line 33, in main
filter_.run(query_string)
File "/home/bb/.local/lib/python2.7/site-packages/afew/Filter.py",
line 61, in run
self.handle_message(message)
File
"/home/bb/.local/lib/python2.7/site-packages/afew/filters/ClassifyingFilter.py",
line 36, in handle_message
scores = self.classifier.classify(extract_mail_body(message))
File "/home/bb/.local/lib/python2.7/site-packages/afew/utils.py",
line 101, in extract_mail_body
raw_payload = raw_payload.decode(encoding, 'replace')
File "/usr/lib/python2.7/encodings/utf_8.py", line 16, in decode
return codecs.utf_8_decode(input, errors, True)
UnicodeEncodeError: 'ascii' codec can't encode character u'\xf6' in
position 239: ordinal not in range(128)
I am using ffb0cc1 of afew and
e02c179c8f6cddcc0b6457ccd0fd40186c75e3db of notmuch.
Running afew --move-mail crashes if one of the files in the notmuch database was previously deleted. This is due to the exception handling in Mailmover.py The shutil-Copy routine (l. 75) raises an exception if the file was not found and the exception-handler only takes care of "already exists" errors.
If the file was not found, it should be reported but not crash afew.
Hi,
I'd like to move mails matching certain criteria from INBOX to INBOX/some_subfolder and therefore put a rule like
INBOX = 'tag:some_tag':INBOX/some_subfolder
into my config.
On the first run, everything is moved as it should be, but on subsequent runs, as afew apparently scans mails in INBOX recursively, all mails which have already been moved to INBOX/some_subfolder would be copied to itself, which makes 'shutil' throw an error.
I think that this behaviour severely limits the MailMover functionality, as no nested folder hierarchies are possible. A good and simple solution would be to check if source and destination are the same and in this case simply skip. Even better, one could additionally implement a 'recursive' option, which toggles recursive scanning of the specified folders.
I apply a move filter moving old mails from a folder Friends
to a folder Archive.Friends
.
Because notmuch finds the latter folder also in a folder:Friends
query, afew -m
tries to move a mail to the folder it is already contained in, which leads to a crash.
Could you please add a check whether moving is actually required before trying to move?
Thank you!
I'm getting the following syntax error when running afew.
garnet:~ $ ~/.local/bin/afew --help
Traceback (most recent call last):
File "/home/svend/.local/bin/afew", line 27, in <module>
from afew.main import main
File "/home/svend/.local/lib/python2.6/site-packages/afew/__init__.py", line 21, in <module>
from .filters import *
File "/home/svend/.local/lib/python2.6/site-packages/afew/filters/ClassifyingFilter.py", line 22, in <module>
from ..DBACL import DBACL as Classifier, ClassificationError
File "/home/svend/.local/lib/python2.6/site-packages/afew/DBACL.py", line 51
for key, value in os.environ.items()
^
SyntaxError: invalid syntax
Python version is 2.6.6.
Some of my lists (vim_use, vim_dev) have _ in the list name like this:
List-ID: <vim_use.googlegroups.com>
The ListMailsFilter.py regex '[a-z0-9-]+'
fail to recognize the list id and don't tag it because the "_".
The List-Id header is define on rfc2919 and the dot-atom-text on rfc2822.
I think that when can include the characters define as atext (defined on rfc2822) and use "[a-zA-Z0-9!#$%&'*+-/=?^_
{|}~]"` in the regex and we can remove the @ as @ can't be present.
Or implement the grammar that define List-Id so <vim.use.google.com> is tagged with vim.use
What you think?
Using 8abd64b (fix for #34) and python 2.7.2+
When running
$ afew -v -v -d --classify -- tag:inbox
I always end up with:
Traceback (most recent call last):
File "/home/nrl/local/bin/afew", line 189, in
main(options, query_string)
File "/home/nrl/local/lib/python2.7/site-packages/afew/main.py", line 69, in main
print('%s --> %s' % (message, category))
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 1: ordinal not in range(128)
This might be a problem specific to my setup (fresh debian testing, python 2.7.8), but I thought I'd give it a go here..
I have a script that pulls mails, and calls notmuch and afew, roughtly as below.
#!/bin/bash
# look up pid of running gnome-keyring-daemon to unlock passwds
die() {
# notify me about error via desktop notifications
exit 1
}
index() {
echo ------------------------ NOTMUCH ------------------------
/usr/local/bin/notmuch new || die "NOTMUCH new failed"
echo ------------------------ AFEW ------------------------
/home/pazz/.local/bin/afew -v -t -n -C /home/pazz/.notmuch-config
echo ---------------------------------------------------------
}
set -e
nm-online -x # stop if not online
/usr/bin/mbsync $@ uow || die "UOW failed"
/usr/bin/mbsync $@ gmail || die "GMAIL failed"
index
date
Works fine when triggered manually. In particular, I get afew's verbose log
messages.
Now when I call this script from cron, it seems that afew is not called at all:
On standart out I get:
...
------------------------ NOTMUCH ------------------------
Processed 42 total files in almost no time.
No new mail.
------------------------ AFEW ------------------------
----------------------------------------------------------
Sat 14 Feb 14:52:09 GMT 2015
First question: why does afew -v
print to stderr, and not to stdout?
Secondly, even the standart err contains nothing of afew:
i get some notmuch error messages complaining about nonmail (mbsync status) files,
but no output from afew.
Also, afew seems not to have run: new messages carry the new
tag and are not tagged otherwise.
It seems afew died silently on me.
Any suggestions?
[edit] and by "silently", i mean not doing anything while still exiting with return code 0.
Hi,
just tried to build custom filters to reflect my static filtering rules. I presume the syntax below is as intended?
# global configuration
[global]
# This is the default filter chain
[SpamFilter]
#[ClassifyingFilter]
#[KillThreadsFilter]
[ListMailsFilter]
[ArchiveSentMailsFilter]
[Filter.1]
query = peergroup
tag = +peergroup
message = ****peergroup filter*
[Filter.2]
query = subject:alot
tag = +alot
message = ****alot*****
[InboxFilter]
i have a message tagged with new matching the query "is:new AND peergroup", but afew wouldn't tag it according to the
log:
pazz@brick:~/projects/afew$ afew -t --new -d -vv
INFO:root:Tagging spam messages
DEBUG:root:Executing query u'(tag:new)'
INFO:root:I would commit changes to 0 messages
INFO:root:Tagging mailing list posts
DEBUG:root:Executing query u'((tag:new)) AND (NOT tag:lists)'
DEBUG:root:Adding tags lists, alot to Justus Winter <reply+i-2624298-4d926afc59836ca6477a8b3178d092598408302e-628455@reply.github.com> (inbox new) (2011-12-21)
DEBUG:root:Adding tags lists, peergroup to Daniel Kreischer <[email protected]> (inbox killed list new) (2011-12-20)
DEBUG:root:Adding tags lists, peergroup to Sascha Steinbiss <[email protected]> (inbox killed list new) (2011-12-19)
DEBUG:root:Adding tags lists, peergroup to Daniel Kreischer <[email protected]> (inbox killed list new) (2011-12-19)
INFO:root:I would commit changes to 4 messages
INFO:root:Archiving all mails sent by myself
DEBUG:root:Executing query u'((tag:new)) AND (from:"[email protected]" OR from:"[email protected]")'
INFO:root:I would commit changes to 0 messages
INFO:root:****peergroup filter*
DEBUG:root:Executing query u'((tag:new)) AND (peergroup)'
INFO:root:I would commit changes to 0 messages
INFO:root:****alot*****
DEBUG:root:Executing query u'((tag:new)) AND (subject:alot)'
INFO:root:I would commit changes to 0 messages
Because afew is only checking for the existence of a query
attribute when generating the query for notmuch, there are errors if query
exists but is empty or None
.
I'd love to have a cmdline option to have mails tagged with the name of then maildir folder they come from:
for folder_ in maildir:
notmuch tag +folder_ +inbox -new -- tag:new and folder:folder_
Potentially one would want some transformations for special folders though:
Sent -> sent
Junk -> spam
dtk
Is there a reason this isn't listed on pypi?
$ afew --dry-run -vv --tag --new --enable-filters=SpamFilter
Traceback (most recent call last):
File "/home/dtk/.local/bin/afew", line 167, in <module>
main(options, query_string)
File "/home/dtk/.local/lib/python2.7/site-packages/afew/main.py", line 32, in main
filter_.run(query_string)
TypeError: unbound method run() must be called with SpamFilter instance as first argument (got str instance instead)
$
Hi there,
While toying with the Debian packaging tools to gauge amount of work required (see also #53), I came across some missing copyright statements.
sagi@wheezy-compile:~$ licensecheck -r afew-0~140530/
afew-0~140530/afew/utils.py: ISC
afew-0~140530/afew/commands.py: ISC
afew-0~140530/afew/FilterRegistry.py: ISC
afew-0~140530/afew/main.py: ISC
afew-0~140530/afew/MailMover.py: ISC
afew-0~140530/afew/filters/ArchiveSentMailsFilter.py: ISC
afew-0~140530/afew/filters/ClassifyingFilter.py: ISC
afew-0~140530/afew/filters/BaseFilter.py: ISC
afew-0~140530/afew/filters/SpamFilter.py: ISC
afew-0~140530/afew/filters/KillThreadsFilter.py: ISC
afew-0~140530/afew/filters/__init__.py: ISC
afew-0~140530/afew/filters/ListMailsFilter.py: ISC
afew-0~140530/afew/filters/SentMailsFilter.py: ISC
afew-0~140530/afew/filters/InboxFilter.py: ISC
afew-0~140530/afew/filters/FolderNameFilter.py: ISC
afew-0~140530/afew/filters/HeaderMatchingFilter.py: *No copyright* UNKNOWN
afew-0~140530/afew/__init__.py: ISC
afew-0~140530/afew/Database.py: ISC
afew-0~140530/afew/tests/__init__.py: *No copyright* UNKNOWN
afew-0~140530/afew/tests/test_settings.py: *No copyright* UNKNOWN
afew-0~140530/afew/files.py: ISC
afew-0~140530/afew/Settings.py: ISC
afew-0~140530/afew/NotmuchSettings.py: ISC
afew-0~140530/afew/DBACL.py: ISC
afew-0~140530/afew/configparser.py: ISC
afew-0~140530/docs/source/conf.py: *No copyright* GENERATED FILE
afew-0~140530/setup.py: ISC
filters/HeaderMatchingFilter.py
contains work by @pazz, @teythoon, @do3cc and @larsks
tests/__init__.py
and tests/test_settings.py
were created/modified by @do3cc
docs/source/conf.py
is autogenerated by sphinx, created by @teythoon
May I suggest adding copyright/license headings to these four files?
I'm trying to learn classifications for mails sent by logwatch (http://ix.io/3kv). I found that strip_signatures() tries to guess a sig which removes the whole body of these mails.
I have no idea how to reliably detect signatures, but maybe you could add an option to disable signature stripping at all? TBH I don't see the point in stripping them anyway ...
apparently gmail lets you export the tagging rules defined for gmail as XML file.
some pointers here: http://googlesystem.blogspot.co.uk/2009/03/export-gmail-filters.html
it would be nice to either automatically create static filters for afew or have some sort of
"Gmail filter" that reads this file and acts accordingly.
This has a very low priority, I just mentioned this here in case you run out of feature requests to work on :)
canonical example might be ham vs spam. but it happens more often with categories that are not as big.
For instance when using:
afew -e ArchiveSentMailsFilter -a
I found no way to set the sent_tag option. In particular putting it in the config was useless.
Hej I am getting null pointer errors from notmuch 8dc8495010057202b725ac029831c03f4e3ab6bd:
Traceback (most recent call last):
File "/home/bb/.local/bin/afew", line 189, in
main(options, query_string)
File "/home/bb/.local/lib/python2.7/site-packages/afew/main.py", line 33, in main
filter_.run(query_string)
File "/home/bb/.local/lib/python2.7/site-packages/afew/Filter.py", line 61, in run
self.handle_message(message)
File "/home/bb/.local/lib/python2.7/site-packages/afew/filters/ListMailsFilter.py", line 31, in handle_message
list_id_header = message.get_header('List-Id')
File "/usr/local/lib/python2.7/dist-packages/notmuch/message.py", line 233, in get_header
raise NullPointerError()
notmuch.errors.NullPointerError
Since space is cheap, I like to be able to synchronize back most notmuch-tags as IMAP folders. The easiest way to do that, for me, is by having a flat folder structure, one folder per tag, and then simply copy the mail into each folder that corresponds to a tag. I tried to get this behaviour by using a MailMover configuration like INBOX = 'tag:inbox':INBOX 'tag:test':test
, but this tries to move the mail on top of the existing one (crashing afew) and would probably still remove it afterwards even if the move failed gracefully.
What I would like is to be able to target the current folder, as above, which would then simply result in the mail not being removed after copying it to any other destinations. Is this a feasible feature?
The next step could be a general copy-feature which could work as follows. Specify a list of tags to apply this to. afew could then, for each tag, do a notmuch-query that finds messages tagged with that tag but not present in the folder with the corresponding name (could also do this with tag:folder-pairs). For each of these messages, find a source file to copy from (possibly need to iterate over all source files if it has more than one, to account for removals from IMAP), and copy it into the destination directory. Then, turn it around: for each tag, do a notmuch-query that finds messages present in the folder with the corresponding name but not tagged with that tag. Remove these messages. (This could also be done in FolderNameFilter.)
Now perform a notmuch new to detect the additions / removals (or perhaps do it directly in the db for each message, might be more reliable w.r.t. synchronization issues).
I've tried my hand at implementing a Python script to do only this a few times now, and each time I get bogged down in details of "what happens if IMAP synchronization happens before this / after this". Perhaps we can solve this in afew.
you should mention the exact format of a sections 'tags' option:
i thought i'd do a tags = +foo,-bar
, but you seem to split via spaces. how do i add tagstrings that contain spaces?
Hi,
https://afew.readthedocs.org/en/latest/extending.html
I followed the example above to extend afew but ran into some issues with the import statements and getting the filter to register.
In the end I got this to work
from afew.FilterRegistry import register_filter
from afew.filters.BaseFilter import Filter
I was looking for a "Full Sample Config", and found it in the docs :)
But it absolutely did not work, throwing a "SyntaxError('Malformed section title %r.' % section)" with section == Filter.notmuch
The reason: the section does not match the regexp.
You either need to specify an index or a parent class after the - index seperated by ".", parent_class put in parantheses. So those examples in the Full Config should read "Filter(notmuch)" (but there should be an existing "notmuch" filter, as far as I understood the filters docs)
Hi,
I've pulled the latest commit ef51300 and get the following error (all filters in afew's config enabled, my [new] section in notmuch-config reads 'tags = new' ):
Traceback (most recent call last):
File "/usr/bin/afew", line 139, in
query_string = get_notmuch_new_query()
File "/usr/lib/python2.7/site-packages/afew/NotmuchSettings.py", line 36, in get_notmuch_new_query
return '(%s)' % ' AND '.join('tag:%s' % tag for tag in get_notmuch_new_tags())
File "/usr/lib/python2.7/site-packages/afew/NotmuchSettings.py", line 33, in get_notmuch_new_tags
return notmuch_settings.get_list('new', 'tags')
File "/usr/lib/python2.7/site-packages/afew/configparser.py", line 35, in get_list
return filter(None, result)
File "/usr/lib/python2.7/site-packages/afew/configparser.py", line 30, in
for value in self.get(section, key).split(delimiter))
TypeError: descriptor 'strip' requires a 'str' object but received a 'unicode'
[1] 29846 exit 1 afew --dry-run --tag --new -vvv
Looks like a pesky unicode problem again :-)
Hi,
When processing the FolderNameFilter, afew crashes with the error
Traceback (most recent call last):
File "/usr/bin/afew", line 169, in
main(options, query_string)
File "/usr/lib/python2.7/site-packages/afew/main.py", line 33, in main
filter_.run(query_string)
File "/usr/lib/python2.7/site-packages/afew/Filter.py", line 60, in run
self.handle_message(message)
File "/usr/lib/python2.7/site-packages/afew/filters/FolderNameFilter.py", line 44, in handle_message
folders, message.get_header('subject').encode('utf8')))
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 1: ordinal not in range(128)
if there are strange Characters in the subject (in my case, French accents and German umlauts in a mail sent over an MS Exchange server). After commenting out lines 44/55 in FolderNameFilter.py, i.e.
logging.debug('found folders {0} for message '{1}''.format(
folders, message.get_header('subject').encode('utf8')))
everything works fine again, so I guess it's some encoding problem. Maybe the log-message should be transformed into ASCII before logging. Unfortunately I'm don't know enough Python to fix this myself
Best,
Simon
[~] afew -t -a 1 ↵
Error opening /home/pazz/mail//home/pazz/Maildir/Sent/new/1345574901.M170094P32649Q1.brick:2,S: No such file or directory
Traceback (most recent call last):
File "/home/pazz/.local/bin/afew", line 189, in <module>
main(options, query_string)
File "/home/pazz/.local/lib/python2.7/site-packages/afew/main.py", line 33, in main
filter_.run(query_string)
File "/home/pazz/.local/lib/python2.7/site-packages/afew/Filter.py", line 61, in run
self.handle_message(message)
File "/home/pazz/.local/lib/python2.7/site-packages/afew/filters/SpamFilter.py", line 32, in handle_message
if message.get_header('X-Spam-Flag') == 'YES':
File "/home/pazz/.local/lib/python2.7/site-packages/notmuch/message.py", line 233, in get_header
raise NullPointerError()
notmuch.errors.NullPointerError
afew is a cool tool which could be added to various distribution repositories. I have added afew to my experimental Gentoo repo and I am looking forward to add first official release of afew to official Gentoo repository. The list of issues is not so long, so I think fixing them and making a release should be so time-consuming.
Mbsync/isync (a popular offline IMAP syncer) stores per-Maildir-folder UIDs by default in the filename of each message. When moving messages between folders, Afew keeps the filename of the message the same, which can result in UID clashes.
Mbsync can use an alternative UID system which gets around this problem, but it may make sense to generate new filenames (this might be complicated by the fact that many Maildir implementations also store mail flags in the filename). At the very least, we should probably warn against using afew with mbsync in this configuration.
bb@ygramul: ~/repos/afew.git (git)-[master] % python setup.py install --prefix=/home/bb/.local/stow/afew && cds && stow afew && cdr
running install
running bdist_egg
running egg_info
creating afew.egg-info
writing requirements to afew.egg-info/requires.txt
writing afew.egg-info/PKG-INFO
writing top-level names to afew.egg-info/top_level.txt
writing dependency_links to afew.egg-info/dependency_links.txt
writing entry points to afew.egg-info/entry_points.txt
writing manifest file 'afew.egg-info/SOURCES.txt'
reading manifest file 'afew.egg-info/SOURCES.txt'
writing manifest file 'afew.egg-info/SOURCES.txt'
installing library code to build/bdist.linux-x86_64/egg
running install_lib
running build_py
copying afew/main.py -> build/lib.linux-x86_64-2.7/afew
copying afew/Settings.py -> build/lib.linux-x86_64-2.7/afew
copying afew/DBACL.py -> build/lib.linux-x86_64-2.7/afew
copying afew/commands.py -> build/lib.linux-x86_64-2.7/afew
copying afew/FilterRegistry.py -> build/lib.linux-x86_64-2.7/afew
copying afew/init.py -> build/lib.linux-x86_64-2.7/afew
creating build/lib.linux-x86_64-2.7/afew/tests
copying afew/tests/test_settings.py -> build/lib.linux-x86_64-2.7/afew/tests
copying afew/tests/init.py -> build/lib.linux-x86_64-2.7/afew/tests
copying afew/filters/SpamFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/ListMailsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/SentMailsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/HeaderMatchingFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/BaseFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/ClassifyingFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/FolderNameFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/ArchiveSentMailsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/KillThreadsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/InboxFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
creating build/bdist.linux-x86_64
creating build/bdist.linux-x86_64/egg
creating build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/main.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/Settings.py -> build/bdist.linux-x86_64/egg/afew
creating build/bdist.linux-x86_64/egg/afew/tests
copying build/lib.linux-x86_64-2.7/afew/tests/test_settings.py -> build/bdist.linux-x86_64/egg/afew/tests
copying build/lib.linux-x86_64-2.7/afew/tests/init.py -> build/bdist.linux-x86_64/egg/afew/tests
copying build/lib.linux-x86_64-2.7/afew/Database.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/NotmuchSettings.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/DBACL.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/Filter.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/configparser.py -> build/bdist.linux-x86_64/egg/afew
creating build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/SpamFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/ListMailsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/SentMailsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/HeaderMatchingFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/BaseFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/init.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/ClassifyingFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/FolderNameFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/ArchiveSentMailsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/KillThreadsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/InboxFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/commands.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/FilterRegistry.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/init.py -> build/bdist.linux-x86_64/egg/afew
creating build/bdist.linux-x86_64/egg/afew/defaults
copying build/lib.linux-x86_64-2.7/afew/defaults/afew.config -> build/bdist.linux-x86_64/egg/afew/defaults
copying build/lib.linux-x86_64-2.7/afew/files.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/utils.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/MailMover.py -> build/bdist.linux-x86_64/egg/afew
byte-compiling build/bdist.linux-x86_64/egg/afew/main.py to main.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/Settings.py to Settings.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/tests/test_settings.py to test_settings.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/tests/init.py to init.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/Database.py to Database.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/NotmuchSettings.py to NotmuchSettings.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/DBACL.py to DBACL.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/Filter.py to Filter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/configparser.py to configparser.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/SpamFilter.py to SpamFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/ListMailsFilter.py to ListMailsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/SentMailsFilter.py to SentMailsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/HeaderMatchingFilter.py to HeaderMatchingFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/BaseFilter.py to BaseFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/init.py to init.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/ClassifyingFilter.py to ClassifyingFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/FolderNameFilter.py to FolderNameFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/ArchiveSentMailsFilter.py to ArchiveSentMailsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/KillThreadsFilter.py to KillThreadsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/InboxFilter.py to InboxFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/commands.py to commands.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/FilterRegistry.py to FilterRegistry.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/init.py to init.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/files.py to files.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/utils.py to utils.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/MailMover.py to MailMover.pyc
creating build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/PKG-INFO -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/SOURCES.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/dependency_links.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/entry_points.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/requires.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/top_level.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
zip_safe flag not set; analyzing archive contents...
afew.Settings: module references file
afew.filters.init: module references file
creating dist
creating 'dist/afew-0.0.0-py2.7.egg' and adding 'build/bdist.linux-x86_64/egg' to it
removing 'build/bdist.linux-x86_64/egg' (and everything under it)
Creating /home/bb/.local/stow/afew/lib/python2.7/site-packages/site.py
Processing afew-0.0.0-py2.7.egg
creating /home/bb/.local/stow/afew/lib/python2.7/site-packages/afew-0.0.0-py2.7.egg
Extracting afew-0.0.0-py2.7.egg to /home/bb/.local/stow/afew/lib/python2.7/site-packages
Adding afew 0.0.0 to easy-install.pth file
Installing afew script to /home/bb/.local/stow/afew/bin
Installed /home/bb/.local/stow/afew/lib/python2.7/site-packages/afew-0.0.0-py2.7.egg
Processing dependencies for afew==0.0.0
Searching for subprocess32
Reading http://pypi.python.org/simple/subprocess32/
Reading http://code.google.com/p/python-subprocess32/
Best match: subprocess32 3.2.5rc1
Downloading https://python-subprocess32.googlecode.com/files/subprocess32-3.2.5rc1.tar.gz#md5=f5f46106368be6336b54af95d048fea9
Processing subprocess32-3.2.5rc1.tar.gz
Writing /tmp/easy_install-1mnN0F/subprocess32-3.2.5rc1/setup.cfg
Running subprocess32-3.2.5rc1/setup.py -q bdist_egg --dist-dir /tmp/easy_install-1mnN0F/subprocess32-3.2.5rc1/egg-dist-tmp-Eyency
warning: no files found matching '.h'
no previously-included directories found matching 'build'
no previously-included directories found matching 'dist'
no previously-included directories found matching '.hg'
_posixsubprocess.c:3:20: fatal error: Python.h: No such file or directory
compilation terminated.
error: Setup script exited with error: command 'x86_64-linux-gnu-gcc' failed with exit status 1
$ afew -vv --learn spam -- tag:spam
DEBUG:root:executing [u'dbacl', u'-T', u'email', u'-l', u'/home/adborden/.local/share/afew/categories/spam']
DEBUG:root:Executing query u'tag:spam'
$ ls ~/.local/share/afew/categories/
important
I have 6 messages tagged as spam. Will dbacl not create a category file if there's not enough data?
I just updated afew from git master and did a python ./setup.py install --user
to install this new checkout.
So It turns out this tries to pull a (new?) dependency "subprocess32"
from pypi, which needs python headers to compile (see trace at the bottom of this post).
I do have a subprocess module installed and working:
ipython -c "import subprocess; print subprocess"
<module 'subprocess' from '/usr/lib/python2.7/subprocess.pyc'>
what's going on?
python ./setup.py install --user ✭master
running install
running bdist_egg
running egg_info
creating afew.egg-info
writing requirements to afew.egg-info/requires.txt
writing afew.egg-info/PKG-INFO
writing top-level names to afew.egg-info/top_level.txt
writing dependency_links to afew.egg-info/dependency_links.txt
writing entry points to afew.egg-info/entry_points.txt
writing manifest file 'afew.egg-info/SOURCES.txt'
reading manifest file 'afew.egg-info/SOURCES.txt'
writing manifest file 'afew.egg-info/SOURCES.txt'
installing library code to build/bdist.linux-x86_64/egg
running install_lib
running build_py
copying afew/commands.py -> build/lib.linux-x86_64-2.7/afew
copying afew/MailMover.py -> build/lib.linux-x86_64-2.7/afew
copying afew/files.py -> build/lib.linux-x86_64-2.7/afew
copying afew/Database.py -> build/lib.linux-x86_64-2.7/afew
copying afew/DBACL.py -> build/lib.linux-x86_64-2.7/afew
copying afew/Settings.py -> build/lib.linux-x86_64-2.7/afew
copying afew/__init__.py -> build/lib.linux-x86_64-2.7/afew
copying afew/FilterRegistry.py -> build/lib.linux-x86_64-2.7/afew
copying afew/main.py -> build/lib.linux-x86_64-2.7/afew
copying afew/filters/ClassifyingFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/KillThreadsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/ArchiveSentMailsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/ListMailsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/InboxFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/BaseFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/FolderNameFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/SentMailsFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/HeaderMatchingFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
copying afew/filters/SpamFilter.py -> build/lib.linux-x86_64-2.7/afew/filters
creating build/lib.linux-x86_64-2.7/afew/tests
copying afew/tests/test_settings.py -> build/lib.linux-x86_64-2.7/afew/tests
copying afew/tests/__init__.py -> build/lib.linux-x86_64-2.7/afew/tests
copying afew/defaults/afew.config -> build/lib.linux-x86_64-2.7/afew/defaults
creating build/bdist.linux-x86_64
creating build/bdist.linux-x86_64/egg
creating build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/NotmuchSettings.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/commands.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/configparser.py -> build/bdist.linux-x86_64/egg/afew
creating build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/ClassifyingFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/KillThreadsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/ArchiveSentMailsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/ListMailsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/InboxFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/BaseFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/FolderNameFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/SentMailsFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/__init__.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/HeaderMatchingFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/filters/SpamFilter.py -> build/bdist.linux-x86_64/egg/afew/filters
copying build/lib.linux-x86_64-2.7/afew/utils.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/MailMover.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/files.py -> build/bdist.linux-x86_64/egg/afew
creating build/bdist.linux-x86_64/egg/afew/defaults
copying build/lib.linux-x86_64-2.7/afew/defaults/afew.config -> build/bdist.linux-x86_64/egg/afew/defaults
copying build/lib.linux-x86_64-2.7/afew/Database.py -> build/bdist.linux-x86_64/egg/afew
creating build/bdist.linux-x86_64/egg/afew/tests
copying build/lib.linux-x86_64-2.7/afew/tests/test_settings.py -> build/bdist.linux-x86_64/egg/afew/tests
copying build/lib.linux-x86_64-2.7/afew/tests/__init__.py -> build/bdist.linux-x86_64/egg/afew/tests
copying build/lib.linux-x86_64-2.7/afew/DBACL.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/Settings.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/Filter.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/__init__.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/FilterRegistry.py -> build/bdist.linux-x86_64/egg/afew
copying build/lib.linux-x86_64-2.7/afew/main.py -> build/bdist.linux-x86_64/egg/afew
byte-compiling build/bdist.linux-x86_64/egg/afew/NotmuchSettings.py to NotmuchSettings.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/commands.py to commands.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/configparser.py to configparser.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/ClassifyingFilter.py to ClassifyingFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/KillThreadsFilter.py to KillThreadsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/ArchiveSentMailsFilter.py to ArchiveSentMailsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/ListMailsFilter.py to ListMailsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/InboxFilter.py to InboxFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/BaseFilter.py to BaseFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/FolderNameFilter.py to FolderNameFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/SentMailsFilter.py to SentMailsFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/__init__.py to __init__.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/HeaderMatchingFilter.py to HeaderMatchingFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/filters/SpamFilter.py to SpamFilter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/utils.py to utils.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/MailMover.py to MailMover.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/files.py to files.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/Database.py to Database.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/tests/test_settings.py to test_settings.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/tests/__init__.py to __init__.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/DBACL.py to DBACL.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/Settings.py to Settings.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/Filter.py to Filter.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/__init__.py to __init__.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/FilterRegistry.py to FilterRegistry.pyc
byte-compiling build/bdist.linux-x86_64/egg/afew/main.py to main.pyc
creating build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/PKG-INFO -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/SOURCES.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/dependency_links.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/entry_points.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/requires.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
copying afew.egg-info/top_level.txt -> build/bdist.linux-x86_64/egg/EGG-INFO
zip_safe flag not set; analyzing archive contents...
afew.Settings: module references __file__
afew.filters.__init__: module references __file__
creating dist
creating 'dist/afew-0.0.0-py2.7.egg' and adding 'build/bdist.linux-x86_64/egg' to it
removing 'build/bdist.linux-x86_64/egg' (and everything under it)
Processing afew-0.0.0-py2.7.egg
creating /home/pazz/.local/lib/python2.7/site-packages/afew-0.0.0-py2.7.egg
Extracting afew-0.0.0-py2.7.egg to /home/pazz/.local/lib/python2.7/site-packages
Adding afew 0.0.0 to easy-install.pth file
Installing afew script to /home/pazz/.local/bin
Installed /home/pazz/.local/lib/python2.7/site-packages/afew-0.0.0-py2.7.egg
Processing dependencies for afew==0.0.0
Searching for subprocess32
Reading https://pypi.python.org/simple/subprocess32/
Reading http://code.google.com/p/python-subprocess32/
Best match: subprocess32 3.2.6
Downloading https://pypi.python.org/packages/source/s/subprocess32/subprocess32-3.2.6.zip#md5=aff53287b000dc5c1dd703c517fac631
Processing subprocess32-3.2.6.zip
Writing /tmp/easy_install-8QRwD4/subprocess32-3.2.6/setup.cfg
Running subprocess32-3.2.6/setup.py -q bdist_egg --dist-dir /tmp/easy_install-8QRwD4/subprocess32-3.2.6/egg-dist-tmp-lUEHs5
warning: no files found matching '*.h'
no previously-included directories found matching 'build'
no previously-included directories found matching 'dist'
no previously-included directories found matching '.hg*'
_posixsubprocess.c:3:20: fatal error: Python.h: No such file or directory
#include "Python.h"
^
compilation terminated.
error: Setup script exited with error: command 'x86_64-linux-gnu-gcc' failed with exit status 1
The sample config, which is the only place I can find reference to a static filter, has this:
# [Filter.1]
# query = from:[email protected]
# tag = +office
Which I banged my head against for a while, until I saw #22 and saw in the comments that it has to be "tags", not "tag".
In general, I think the documentation on this could be improved - it seems a little bit crazy that there isn't an example of a static filter in the documentation page on filters!
Due to how afew's configuration is parsed the MailMover is unable to handle folder names containing spaces.
This is a problem for Gmail accounts synced with offlineimap which include folder name like, "[Google Mail]", "Sent Mail" and "All Mail".
Replacing the spaces with non-breaking spaces doesn't help since Python's string.split()
and re.split("\s+", ...)
treat them the same as regular spaces.
When upgrading my Linux distro I migrated all of my mail, notmuch database and my offlineimap/afew/alot toolchain successfully from the old distro to the new with the minor exception that I somehow managed to remove ~/.local/share/afew/categories.
This caused 90% of my mail (both old and new) to get tagged as "flagged" by afew. Over 9000 messages in total. I added back the empty categories directory, removed all instances of the "tagged" flag with,
notmuch tag -flagged "*"
And now things are working again. Seems like afew should fail more gracefully in the absence of the categories directory even output some error.
Hi,
with no classifications setup, a run of the classifying filter throws the error
INFO:root:Tagging via classification
DEBUG:root:Executing query u''
DEBUG:root:executing [u'dbacl', u'-n']
Traceback (most recent call last):
File "/usr/bin/afew", line 169, in
main(options, query_string)
File "/usr/lib/python2.7/site-packages/afew/main.py", line 33, in main
filter_.run(query_string)
File "/usr/lib/python2.7/site-packages/afew/Filter.py", line 60, in run
self.handle_message(message)
File "/usr/lib/python2.7/site-packages/afew/filters/ClassifyingFilter.py", line 33, in handle_message
scores = self.classifier.classify(extract_mail_body(message))
File "/usr/lib/python2.7/site-packages/afew/DBACL.py", line 108, in classify
raise BackendError('dbacl classification failed:\n%s' % stderr)
afew.DBACL.BackendError: dbacl classification failed:
dbacl:error: please use either -c or -l option.
Best,
Simon
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.