Re: [RFC] reordering and cleanup of thread authors

2010-04-21 Thread Dirk Hohndel
On Fri, 09 Apr 2010 19:42:49 -0700, Dirk Hohndel hohn...@infradead.org wrote:
 On Sat, 10 Apr 2010 03:53:59 +0200, Michal Sojka sojk...@fel.cvut.cz wrote:
  I think that using | as a separator would help here. Let's say that
  initially we have Matched Author, Non Matched, Matched Again we can
  tranform this to  Matched Author, Matched Again| Non Matched. This way,
  the length of the string remains the same. If there is no | after
  transformation, we know that all authors matched because there is always
  at least one mathed author in the search results.
 
 That's a great idea. I'll update the patch to do that.

Since Carl just prompted me, I wrote an updated patch (will post in a
separate message replying to this one). 

I made the change suggested by Michal, fixed a bug or two and removed
the part of the patch that was trying to cleanup author names in Last,
First format - on IRC it was pointed out to me that I was overlooking
another use of the ',' in email addresses: accounts that are shared by
multiple people. And it makes no sense to reorder email addresses of the
form Wife, Husband and child familyacco...@add.res

I haven't given up on this, though. Since Exchange and Outlook have this
nasty habit of creating these Last, First first.l...@company.com or
Last, First MI first.mi.l...@company.com from headers, I really want
to add the option to clean those up. So I'll submit a separate patch
that checks if we have exactly one of these two pattern shown here - and
that then reorders things

/D

-- 
Dirk Hohndel
Intel Open Source Technology Center
___
notmuch mailing list
notmuch@notmuchmail.org
http://notmuchmail.org/mailman/listinfo/notmuch


[RFC] reordering and cleanup of thread authors

2010-04-10 Thread Michal Sojka
On Fri, 09 Apr 2010, Dirk Hohndel wrote:
> On Fri, 09 Apr 2010 08:07:27 +0200, Michal Sojka  
> wrote:
> > On Wed, 07 Apr 2010, Dirk Hohndel wrote:
> > > 
> > > This is based in part on some discussion on IRC today.
> > > When a thread is displayed in the search results, previously the authors
> > > were always displayed in chronological order. But if only part of the
> > > thread matches the query, that may or may not be the intuitive thing to
> > > do.
> > 
> > thanks for the patch. It is a very interesting feature.
> 
> Thanks - I've been using it for a few days now and am fairly happy with
> it.
> 
> > >
> > > +/*
> > > + * move authors of matched messages in the thread to 
> > > + * the front of the authors list, but keep them in
> > > + * oldest first order within their group
> > > + */
> > > +static void
> > > +_thread_move_matched_author (notmuch_thread_t *thread,
> > > +  const char *author)
> > > +{
> > > +char *authorscopy;
> > > +char *currentauthor;
> > > +int idx,nmstart,author_len,authors_len;
> > > +
> > > +if (thread->authors == NULL)
> > > + return;
> > > +if (thread->nonmatched_authors == NULL)
> > > + thread->nonmatched_authors = thread->authors;
> > > +author_len = strlen(author);
> > > +authors_len = strlen(thread->authors);
> > > +if (author_len == authors_len) {
> > > + /* just one author */
> > > + thread->nonmatched_authors += author_len;
> > > + return;
> > > +}
> > > +currentauthor = strcasestr(thread->authors, author);
> > > +if (currentauthor == NULL)
> > > + return;
> > > +idx = currentauthor - thread->nonmatched_authors;
> > > +if (idx < 0) {
> > > + /* already among matched authors */
> > > + return;
> > > +}
> > > +if (thread->nonmatched_authors + author_len < thread->authors + 
> > > authors_len) {
> > 
> > What does the above condition exactly mean? 
> 
> Eh - it's ugly. 
> 
> thread->authors + authors_len points to the trailing '\0' of the list of
> all my authors. At this point in the code we know that the current
> position of this author is at or after nonmatched_authors. So if
> nonmatched_authors + author_len is less than the end of the all authors
> that means that there was another author in the list behind this one -
> and we need to move things around. 
> 
> In the else clause we just move the pointer to nonmatched_authors to the
> end of this author.
> 
> So yeah, ugly, should be rewritten to make it easier to understand (or
> at least commented better).
> 
> > I was not able to decode it
> > and it seems to be wrong. I expect that the "|" is used to delimit
> > matched and non-matched authors. If I run notmuch search
> > thread:, which matches all messages in the thread, I see
> > all authors delimited by "|", which I consider wrong.
> 
> Why do you think it's wrong? 

Because I thought, that | was used as a delimiter between the two parts
of the list and not as a marker of matched authors.

> It's consistent. The thing that I actually DISlike about the current
> solution is that the last author has no delimiter (since there's no
> trailing ',' in the list and I didn't want to realloc the space for
> the authors string). So you can't tell with one glance if all authors
> match or all but the last one match. I haven't come up with a better
> visual way to indicate this...

I think that using | as a separator would help here. Let's say that
initially we have "Matched Author, Non Matched, Matched Again" we can
tranform this to  "Matched Author, Matched Again| Non Matched". This way,
the length of the string remains the same. If there is no | after
transformation, we know that all authors matched because there is always
at least one mathed author in the search results.

-Michal



[RFC] reordering and cleanup of thread authors

2010-04-09 Thread Dirk Hohndel
On Sat, 10 Apr 2010 03:53:59 +0200, Michal Sojka  wrote:
> I think that using | as a separator would help here. Let's say that
> initially we have "Matched Author, Non Matched, Matched Again" we can
> tranform this to  "Matched Author, Matched Again| Non Matched". This way,
> the length of the string remains the same. If there is no | after
> transformation, we know that all authors matched because there is always
> at least one mathed author in the search results.

That's a great idea. I'll update the patch to do that.

/D

-- 
Dirk Hohndel
Intel Open Source Technology Center


[RFC] reordering and cleanup of thread authors

2010-04-09 Thread Dirk Hohndel
On Fri, 09 Apr 2010 08:07:27 +0200, Michal Sojka  wrote:
> On Wed, 07 Apr 2010, Dirk Hohndel wrote:
> > 
> > This is based in part on some discussion on IRC today.
> > When a thread is displayed in the search results, previously the authors
> > were always displayed in chronological order. But if only part of the
> > thread matches the query, that may or may not be the intuitive thing to
> > do.
> 
> thanks for the patch. It is a very interesting feature.

Thanks - I've been using it for a few days now and am fairly happy with
it.

> >
> > +/*
> > + * move authors of matched messages in the thread to 
> > + * the front of the authors list, but keep them in
> > + * oldest first order within their group
> > + */
> > +static void
> > +_thread_move_matched_author (notmuch_thread_t *thread,
> > +const char *author)
> > +{
> > +char *authorscopy;
> > +char *currentauthor;
> > +int idx,nmstart,author_len,authors_len;
> > +
> > +if (thread->authors == NULL)
> > +   return;
> > +if (thread->nonmatched_authors == NULL)
> > +   thread->nonmatched_authors = thread->authors;
> > +author_len = strlen(author);
> > +authors_len = strlen(thread->authors);
> > +if (author_len == authors_len) {
> > +   /* just one author */
> > +   thread->nonmatched_authors += author_len;
> > +   return;
> > +}
> > +currentauthor = strcasestr(thread->authors, author);
> > +if (currentauthor == NULL)
> > +   return;
> > +idx = currentauthor - thread->nonmatched_authors;
> > +if (idx < 0) {
> > +   /* already among matched authors */
> > +   return;
> > +}
> > +if (thread->nonmatched_authors + author_len < thread->authors + 
> > authors_len) {
> 
> What does the above condition exactly mean? 

Eh - it's ugly. 

thread->authors + authors_len points to the trailing '\0' of the list of
all my authors. At this point in the code we know that the current
position of this author is at or after nonmatched_authors. So if
nonmatched_authors + author_len is less than the end of the all authors
that means that there was another author in the list behind this one -
and we need to move things around. 

In the else clause we just move the pointer to nonmatched_authors to the
end of this author.

So yeah, ugly, should be rewritten to make it easier to understand (or
at least commented better).

> I was not able to decode it
> and it seems to be wrong. I expect that the "|" is used to delimit
> matched and non-matched authors. If I run notmuch search
> thread:, which matches all messages in the thread, I see
> all authors delimited by "|", which I consider wrong.

Why do you think it's wrong? It's consistent. The thing that I actually
DISlike about the current solution is that the last author has no
delimiter (since there's no trailing ',' in the list and I didn't want
to realloc the space for the authors string). So you can't tell with one
glance if all authors match or all but the last one match. I haven't
come up with a better visual way to indicate this... 

Suggestions?

/D

-- 
Dirk Hohndel
Intel Open Source Technology Center


[RFC] reordering and cleanup of thread authors

2010-04-09 Thread Michal Sojka
On Wed, 07 Apr 2010, Dirk Hohndel wrote:
> 
> This is based in part on some discussion on IRC today.
> When a thread is displayed in the search results, previously the authors
> were always displayed in chronological order. But if only part of the
> thread matches the query, that may or may not be the intuitive thing to
> do.

Hi Dirk,

thanks for the patch. It is a very interesting feature. See my comments
below.

>
> [...]
>
> +/*
> + * move authors of matched messages in the thread to 
> + * the front of the authors list, but keep them in
> + * oldest first order within their group
> + */
> +static void
> +_thread_move_matched_author (notmuch_thread_t *thread,
> +  const char *author)
> +{
> +char *authorscopy;
> +char *currentauthor;
> +int idx,nmstart,author_len,authors_len;
> +
> +if (thread->authors == NULL)
> + return;
> +if (thread->nonmatched_authors == NULL)
> + thread->nonmatched_authors = thread->authors;
> +author_len = strlen(author);
> +authors_len = strlen(thread->authors);
> +if (author_len == authors_len) {
> + /* just one author */
> + thread->nonmatched_authors += author_len;
> + return;
> +}
> +currentauthor = strcasestr(thread->authors, author);
> +if (currentauthor == NULL)
> + return;
> +idx = currentauthor - thread->nonmatched_authors;
> +if (idx < 0) {
> + /* already among matched authors */
> + return;
> +}
> +if (thread->nonmatched_authors + author_len < thread->authors + 
> authors_len) {

What does the above condition exactly mean? I was not able to decode it
and it seems to be wrong. I expect that the "|" is used to delimit
matched and non-matched authors. If I run notmuch search
thread:, which matches all messages in the thread, I see
all authors delimited by "|", which I consider wrong.

-Michal

> + /* we have to make changes, so let's get a temp copy */
> + authorscopy = strdup(thread->authors);
> + if (authorscopy == NULL)
> + return;
> + /* nmstart is the offset into where the non-matched authors start */
> + nmstart = thread->nonmatched_authors - thread->authors;
> + /* copy this author and add the "| " - the if clause above tells us 
> there's more */
> + strncpy(thread->nonmatched_authors,author,author_len);
> + strncpy(thread->nonmatched_authors+author_len,"| ",2);
> + thread->nonmatched_authors += author_len+2; 
> + if (idx > 0) {
> +   /* we are actually moving authors around, not just changing the 
> separator
> +* first copy the authors that came BEFORE our author */
> +   strncpy(thread->nonmatched_authors, authorscopy+nmstart, idx-2);
> +   /* finally, if there are authors AFTER our author, copy those */
> +   if(author_len+nmstart+idx < authors_len) {
> + strncpy(thread->nonmatched_authors + idx - 2,", ",2);
> + strncpy(thread->nonmatched_authors + idx, authorscopy+nmstart + idx 
> + author_len + 2, 
> + authors_len - (nmstart + idx + author_len + 2));
> +   }
> + }
> + free(authorscopy);
> +} else {
> + thread->nonmatched_authors += author_len;
> +}
> +return;
> +}


Re: [RFC] reordering and cleanup of thread authors

2010-04-09 Thread Michal Sojka
On Wed, 07 Apr 2010, Dirk Hohndel wrote:
 
 This is based in part on some discussion on IRC today.
 When a thread is displayed in the search results, previously the authors
 were always displayed in chronological order. But if only part of the
 thread matches the query, that may or may not be the intuitive thing to
 do.

Hi Dirk,

thanks for the patch. It is a very interesting feature. See my comments
below.


 [...]

 +/*
 + * move authors of matched messages in the thread to 
 + * the front of the authors list, but keep them in
 + * oldest first order within their group
 + */
 +static void
 +_thread_move_matched_author (notmuch_thread_t *thread,
 +  const char *author)
 +{
 +char *authorscopy;
 +char *currentauthor;
 +int idx,nmstart,author_len,authors_len;
 +
 +if (thread-authors == NULL)
 + return;
 +if (thread-nonmatched_authors == NULL)
 + thread-nonmatched_authors = thread-authors;
 +author_len = strlen(author);
 +authors_len = strlen(thread-authors);
 +if (author_len == authors_len) {
 + /* just one author */
 + thread-nonmatched_authors += author_len;
 + return;
 +}
 +currentauthor = strcasestr(thread-authors, author);
 +if (currentauthor == NULL)
 + return;
 +idx = currentauthor - thread-nonmatched_authors;
 +if (idx  0) {
 + /* already among matched authors */
 + return;
 +}
 +if (thread-nonmatched_authors + author_len  thread-authors + 
 authors_len) {

What does the above condition exactly mean? I was not able to decode it
and it seems to be wrong. I expect that the | is used to delimit
matched and non-matched authors. If I run notmuch search
thread:, which matches all messages in the thread, I see
all authors delimited by |, which I consider wrong.

-Michal

 + /* we have to make changes, so let's get a temp copy */
 + authorscopy = strdup(thread-authors);
 + if (authorscopy == NULL)
 + return;
 + /* nmstart is the offset into where the non-matched authors start */
 + nmstart = thread-nonmatched_authors - thread-authors;
 + /* copy this author and add the |  - the if clause above tells us 
 there's more */
 + strncpy(thread-nonmatched_authors,author,author_len);
 + strncpy(thread-nonmatched_authors+author_len,| ,2);
 + thread-nonmatched_authors += author_len+2; 
 + if (idx  0) {
 +   /* we are actually moving authors around, not just changing the 
 separator
 +* first copy the authors that came BEFORE our author */
 +   strncpy(thread-nonmatched_authors, authorscopy+nmstart, idx-2);
 +   /* finally, if there are authors AFTER our author, copy those */
 +   if(author_len+nmstart+idx  authors_len) {
 + strncpy(thread-nonmatched_authors + idx - 2,, ,2);
 + strncpy(thread-nonmatched_authors + idx, authorscopy+nmstart + idx 
 + author_len + 2, 
 + authors_len - (nmstart + idx + author_len + 2));
 +   }
 + }
 + free(authorscopy);
 +} else {
 + thread-nonmatched_authors += author_len;
 +}
 +return;
 +}
___
notmuch mailing list
notmuch@notmuchmail.org
http://notmuchmail.org/mailman/listinfo/notmuch


Re: [RFC] reordering and cleanup of thread authors

2010-04-09 Thread Michal Sojka
On Fri, 09 Apr 2010, Dirk Hohndel wrote:
 On Fri, 09 Apr 2010 08:07:27 +0200, Michal Sojka sojk...@fel.cvut.cz wrote:
  On Wed, 07 Apr 2010, Dirk Hohndel wrote:
   
   This is based in part on some discussion on IRC today.
   When a thread is displayed in the search results, previously the authors
   were always displayed in chronological order. But if only part of the
   thread matches the query, that may or may not be the intuitive thing to
   do.
  
  thanks for the patch. It is a very interesting feature.
 
 Thanks - I've been using it for a few days now and am fairly happy with
 it.
 
  
   +/*
   + * move authors of matched messages in the thread to 
   + * the front of the authors list, but keep them in
   + * oldest first order within their group
   + */
   +static void
   +_thread_move_matched_author (notmuch_thread_t *thread,
   +  const char *author)
   +{
   +char *authorscopy;
   +char *currentauthor;
   +int idx,nmstart,author_len,authors_len;
   +
   +if (thread-authors == NULL)
   + return;
   +if (thread-nonmatched_authors == NULL)
   + thread-nonmatched_authors = thread-authors;
   +author_len = strlen(author);
   +authors_len = strlen(thread-authors);
   +if (author_len == authors_len) {
   + /* just one author */
   + thread-nonmatched_authors += author_len;
   + return;
   +}
   +currentauthor = strcasestr(thread-authors, author);
   +if (currentauthor == NULL)
   + return;
   +idx = currentauthor - thread-nonmatched_authors;
   +if (idx  0) {
   + /* already among matched authors */
   + return;
   +}
   +if (thread-nonmatched_authors + author_len  thread-authors + 
   authors_len) {
  
  What does the above condition exactly mean? 
 
 Eh - it's ugly. 
 
 thread-authors + authors_len points to the trailing '\0' of the list of
 all my authors. At this point in the code we know that the current
 position of this author is at or after nonmatched_authors. So if
 nonmatched_authors + author_len is less than the end of the all authors
 that means that there was another author in the list behind this one -
 and we need to move things around. 
 
 In the else clause we just move the pointer to nonmatched_authors to the
 end of this author.
 
 So yeah, ugly, should be rewritten to make it easier to understand (or
 at least commented better).
 
  I was not able to decode it
  and it seems to be wrong. I expect that the | is used to delimit
  matched and non-matched authors. If I run notmuch search
  thread:, which matches all messages in the thread, I see
  all authors delimited by |, which I consider wrong.
 
 Why do you think it's wrong? 

Because I thought, that | was used as a delimiter between the two parts
of the list and not as a marker of matched authors.

 It's consistent. The thing that I actually DISlike about the current
 solution is that the last author has no delimiter (since there's no
 trailing ',' in the list and I didn't want to realloc the space for
 the authors string). So you can't tell with one glance if all authors
 match or all but the last one match. I haven't come up with a better
 visual way to indicate this...

I think that using | as a separator would help here. Let's say that
initially we have Matched Author, Non Matched, Matched Again we can
tranform this to  Matched Author, Matched Again| Non Matched. This way,
the length of the string remains the same. If there is no | after
transformation, we know that all authors matched because there is always
at least one mathed author in the search results.

-Michal

___
notmuch mailing list
notmuch@notmuchmail.org
http://notmuchmail.org/mailman/listinfo/notmuch


Re: [RFC] reordering and cleanup of thread authors

2010-04-09 Thread Dirk Hohndel
On Sat, 10 Apr 2010 03:53:59 +0200, Michal Sojka sojk...@fel.cvut.cz wrote:
 I think that using | as a separator would help here. Let's say that
 initially we have Matched Author, Non Matched, Matched Again we can
 tranform this to  Matched Author, Matched Again| Non Matched. This way,
 the length of the string remains the same. If there is no | after
 transformation, we know that all authors matched because there is always
 at least one mathed author in the search results.

That's a great idea. I'll update the patch to do that.

/D

-- 
Dirk Hohndel
Intel Open Source Technology Center
___
notmuch mailing list
notmuch@notmuchmail.org
http://notmuchmail.org/mailman/listinfo/notmuch


[RFC] reordering and cleanup of thread authors

2010-04-06 Thread Dirk Hohndel

This is based in part on some discussion on IRC today.
When a thread is displayed in the search results, previously the authors
were always displayed in chronological order. But if only part of the
thread matches the query, that may or may not be the intuitive thing to
do.
Imagine the default "+inbox" query. Those mails in the thread that
match the query are actually "new" (whatever that means). And some
people seem to think that it would be much better to see those author
names first. For example, imagine a long and drawn out thread that once
was started by me; you have long read the older part of the thread and
removed the inbox tag. Whenever a new email comes in on this thread, the
author column in the search display will first show "Dirk Hohndel" - I
think it should first show the actual author(s) of the new mail(s).

The second cleanup that I've done in this context is to convert all
author names into the much easier to parse "Firstname Lastname"
format. Some broken mail systems (cough - Exchange - Cough) seem to
prefer "Lastname, Firstname" - which makes the comma separated list of
authors really hard to parse at one glance. Worse, it creates douplicate
entries if a person happens to show in both orders. So this does a
rather simplistic "look for a comma, if it's there, reorder" approach to
cleaning up the author name.

I don't think this is ready to be pulled. There was a strong request on
IRC to make the re-ordering of the author names configurable. I think
the cleanup of the names (First Last) should be configurable as well.
And of course I wonder about my implementation, given that I'm still
trying to wrap my mind around the current code base.

Thanks

/D

diff --git a/lib/message.cc b/lib/message.cc
index 721c9a6..ac0afd9 100644
--- a/lib/message.cc
+++ b/lib/message.cc
@@ -35,6 +35,7 @@ struct _notmuch_message {
 char *thread_id;
 char *in_reply_to;
 char *filename;
+char *author;
 notmuch_message_file_t *message_file;
 notmuch_message_list_t *replies;
 unsigned long flags;
@@ -110,6 +111,7 @@ _notmuch_message_create (const void *talloc_owner,
 message->in_reply_to = NULL;
 message->filename = NULL;
 message->message_file = NULL;
+message->author = NULL;

 message->replies = _notmuch_message_list_create (message);
 if (unlikely (message->replies == NULL)) {
@@ -533,6 +535,20 @@ notmuch_message_get_tags (notmuch_message_t *message)
 return _notmuch_convert_tags(message, i, end);
 }

+const char *
+notmuch_message_get_author (notmuch_message_t *message)
+{
+return message->author;
+}
+
+void
+notmuch_message_set_author (notmuch_message_t *message,
+   const char *author)
+{
+message->author = talloc_strdup(message, author);
+return;
+}
+
 void
 _notmuch_message_set_date (notmuch_message_t *message,
   const char *date)
diff --git a/lib/notmuch.h b/lib/notmuch.h
index 88da078..79638bb 100644
--- a/lib/notmuch.h
+++ b/lib/notmuch.h
@@ -771,6 +771,17 @@ notmuch_message_set_flag (notmuch_message_t *message,
 time_t
 notmuch_message_get_date  (notmuch_message_t *message);

+/* Set the author member of 'message' - this is the representation used
+ * when displaying the message
+ */
+void
+notmuch_message_set_author (notmuch_message_t *message, const char *author);
+
+/* Get the author member of 'message'
+ */
+const char *
+notmuch_message_get_author (notmuch_message_t *message);
+
 /* Get the value of the specified header from 'message'.
  *
  * The value will be read from the actual message file, not from the
diff --git a/lib/thread.cc b/lib/thread.cc
index 48c070e..c3c83a3 100644
--- a/lib/thread.cc
+++ b/lib/thread.cc
@@ -32,6 +32,7 @@ struct _notmuch_thread {
 char *subject;
 GHashTable *authors_hash;
 char *authors;
+char *nonmatched_authors;
 GHashTable *tags;

 notmuch_message_list_t *message_list;
@@ -69,8 +70,95 @@ _thread_add_author (notmuch_thread_t *thread,
thread->authors = talloc_asprintf (thread, "%s, %s",
   thread->authors,
   author);
-else
+else {
thread->authors = talloc_strdup (thread, author);
+}
+}
+
+/*
+ * move authors of matched messages in the thread to 
+ * the front of the authors list, but keep them in
+ * oldest first order within their group
+ */
+static void
+_thread_move_matched_author (notmuch_thread_t *thread,
+const char *author)
+{
+char *authorscopy;
+char *currentauthor;
+int idx,nmstart,author_len,authors_len;
+
+if (thread->authors == NULL)
+   return;
+if (thread->nonmatched_authors == NULL)
+   thread->nonmatched_authors = thread->authors;
+author_len = strlen(author);
+authors_len = strlen(thread->authors);
+if (author_len == authors_len) {
+   /* just one author */
+   thread->nonmatched_authors += author_len;
+   return;
+}
+   

[RFC] reordering and cleanup of thread authors

2010-04-06 Thread Dirk Hohndel

This is based in part on some discussion on IRC today.
When a thread is displayed in the search results, previously the authors
were always displayed in chronological order. But if only part of the
thread matches the query, that may or may not be the intuitive thing to
do.
Imagine the default +inbox query. Those mails in the thread that
match the query are actually new (whatever that means). And some
people seem to think that it would be much better to see those author
names first. For example, imagine a long and drawn out thread that once
was started by me; you have long read the older part of the thread and
removed the inbox tag. Whenever a new email comes in on this thread, the
author column in the search display will first show Dirk Hohndel - I
think it should first show the actual author(s) of the new mail(s).

The second cleanup that I've done in this context is to convert all
author names into the much easier to parse Firstname Lastname
format. Some broken mail systems (cough - Exchange - Cough) seem to
prefer Lastname, Firstname - which makes the comma separated list of
authors really hard to parse at one glance. Worse, it creates douplicate
entries if a person happens to show in both orders. So this does a
rather simplistic look for a comma, if it's there, reorder approach to
cleaning up the author name.

I don't think this is ready to be pulled. There was a strong request on
IRC to make the re-ordering of the author names configurable. I think
the cleanup of the names (First Last) should be configurable as well.
And of course I wonder about my implementation, given that I'm still
trying to wrap my mind around the current code base.

Thanks

/D

diff --git a/lib/message.cc b/lib/message.cc
index 721c9a6..ac0afd9 100644
--- a/lib/message.cc
+++ b/lib/message.cc
@@ -35,6 +35,7 @@ struct _notmuch_message {
 char *thread_id;
 char *in_reply_to;
 char *filename;
+char *author;
 notmuch_message_file_t *message_file;
 notmuch_message_list_t *replies;
 unsigned long flags;
@@ -110,6 +111,7 @@ _notmuch_message_create (const void *talloc_owner,
 message-in_reply_to = NULL;
 message-filename = NULL;
 message-message_file = NULL;
+message-author = NULL;
 
 message-replies = _notmuch_message_list_create (message);
 if (unlikely (message-replies == NULL)) {
@@ -533,6 +535,20 @@ notmuch_message_get_tags (notmuch_message_t *message)
 return _notmuch_convert_tags(message, i, end);
 }
 
+const char *
+notmuch_message_get_author (notmuch_message_t *message)
+{
+return message-author;
+}
+
+void
+notmuch_message_set_author (notmuch_message_t *message,
+   const char *author)
+{
+message-author = talloc_strdup(message, author);
+return;
+}
+
 void
 _notmuch_message_set_date (notmuch_message_t *message,
   const char *date)
diff --git a/lib/notmuch.h b/lib/notmuch.h
index 88da078..79638bb 100644
--- a/lib/notmuch.h
+++ b/lib/notmuch.h
@@ -771,6 +771,17 @@ notmuch_message_set_flag (notmuch_message_t *message,
 time_t
 notmuch_message_get_date  (notmuch_message_t *message);
 
+/* Set the author member of 'message' - this is the representation used
+ * when displaying the message
+ */
+void
+notmuch_message_set_author (notmuch_message_t *message, const char *author);
+
+/* Get the author member of 'message'
+ */
+const char *
+notmuch_message_get_author (notmuch_message_t *message);
+
 /* Get the value of the specified header from 'message'.
  *
  * The value will be read from the actual message file, not from the
diff --git a/lib/thread.cc b/lib/thread.cc
index 48c070e..c3c83a3 100644
--- a/lib/thread.cc
+++ b/lib/thread.cc
@@ -32,6 +32,7 @@ struct _notmuch_thread {
 char *subject;
 GHashTable *authors_hash;
 char *authors;
+char *nonmatched_authors;
 GHashTable *tags;
 
 notmuch_message_list_t *message_list;
@@ -69,8 +70,95 @@ _thread_add_author (notmuch_thread_t *thread,
thread-authors = talloc_asprintf (thread, %s, %s,
   thread-authors,
   author);
-else
+else {
thread-authors = talloc_strdup (thread, author);
+}
+}
+
+/*
+ * move authors of matched messages in the thread to 
+ * the front of the authors list, but keep them in
+ * oldest first order within their group
+ */
+static void
+_thread_move_matched_author (notmuch_thread_t *thread,
+const char *author)
+{
+char *authorscopy;
+char *currentauthor;
+int idx,nmstart,author_len,authors_len;
+
+if (thread-authors == NULL)
+   return;
+if (thread-nonmatched_authors == NULL)
+   thread-nonmatched_authors = thread-authors;
+author_len = strlen(author);
+authors_len = strlen(thread-authors);
+if (author_len == authors_len) {
+   /* just one author */
+   thread-nonmatched_authors += author_len;
+   return;
+}
+currentauthor =