{"thread":{"id":"18833","subject":"[PATCH RFC 01/10] Docs: send-email: Put options back into alphabetical order","startedAt":"2009-04-11T19:08:19Z","lastAt":"2009-04-13T02:15:38Z","messageCount":23,"participants":["Michael Witten","Sverre Rabbelier","Stephen Boyd","Jay Soffian","Miles Bader"],"isPatch":true,"patchVersion":1,"patchTotal":10},"messages":[{"id":"111059","messageId":"1239476908-25944-1-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":null,"subject":"[PATCH RFC 01/10] Docs: send-email: Put options back into alphabetical order","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:19Z","receivedAt":"2009-04-11T19:08:19Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"I also wrote a comment block as a warning to trespassers.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n Documentation/git-send-email.txt |   26 +++++++++++++++-----------\n 1 files changed, 15 insertions(+), 11 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 0b1f183..595c7ba 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -32,6 +32,10 @@ script\n This format expects the first line of the file to contain the \"Cc:\" value\n and the \"Subject:\" of the message as the second line.\n \n+/////////////////////////////////////////////////////////////////////////////////////\n+//// Within each category (Composing, Sending, Automating, and Administering),   ////\n+//// options are to be given in alphabetical order. Please maintain this layout. ////\n+/////////////////////////////////////////////////////////////////////////////////////\n \n OPTIONS\n -------\n@@ -39,6 +43,11 @@ OPTIONS\n Composing\n ~~~~~~~~~\n \n+--annotate::\n+\tReview each patch you're about to send in an editor. The setting\n+\t'sendemail.multiedit' defines if this will spawn one editor per patch\n+\tor one for all of them at once.\n+\n --bcc=<address>::\n \tSpecify a \"Bcc:\" value for each email. Default is the value of\n \t'sendemail.bcc'.\n@@ -51,11 +60,6 @@ The --bcc option must be repeated for each user you want on the bcc list.\n +\n The --cc option must be repeated for each user you want on the cc list.\n \n---annotate::\n-\tReview each patch you're about to send in an editor. The setting\n-\t'sendemail.multiedit' defines if this will spawn one editor per patch\n-\tor one for all of them at once.\n-\n --compose::\n \tUse $GIT_EDITOR, core.editor, $VISUAL, or $EDITOR to edit an\n \tintroductory message for the patch series.\n@@ -230,6 +234,12 @@ have been specified, in which case default to 'compose'.\n --dry-run::\n \tDo everything except actually send the emails.\n \n+--[no-]format-patch::\n+\tWhen an argument may be understood either as a reference or as a file name,\n+\tchoose to understand it as a format-patch argument ('--format-patch')\n+\tor as a file name ('--no-format-patch'). By default, when such a conflict\n+\toccurs, git send-email will fail.\n+\n --quiet::\n \tMake git-send-email less verbose.  One line per email should be\n \tall that is output.\n@@ -246,12 +256,6 @@ have been specified, in which case default to 'compose'.\n Default is the value of 'sendemail.validate'; if this is not set,\n default to '--validate'.\n \n---[no-]format-patch::\n-\tWhen an argument may be understood either as a reference or as a file name,\n-\tchoose to understand it as a format-patch argument ('--format-patch')\n-\tor as a file name ('--no-format-patch'). By default, when such a conflict\n-\toccurs, git send-email will fail.\n-\n \n CONFIGURATION\n -------------\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111060","messageId":"1239476908-25944-2-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-1-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 02/10] Docs: send-email: Remove superfluous information in CONFIGURATION","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:20Z","receivedAt":"2009-04-11T19:08:20Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"In particular, sendemail.confirm was removed, because it's already\ndescribed along with its corresponding option.\n\nThere is now a comment block warning trespassers.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n Documentation/git-send-email.txt |   11 +++++------\n 1 files changed, 5 insertions(+), 6 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 595c7ba..7cdbdd6 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -257,6 +257,11 @@ Default is the value of 'sendemail.validate'; if this is not set,\n default to '--validate'.\n \n \n+//////////////////////////////////////////////////////////////////////////////\n+//// Only list configuration variables that can't be listed and described ////\n+//// with a corresponding option above                                    ////\n+//////////////////////////////////////////////////////////////////////////////\n+\n CONFIGURATION\n -------------\n \n@@ -274,12 +279,6 @@ sendemail.multiedit::\n \tsummary when '--compose' is used). If false, files will be edited one\n \tafter the other, spawning a new editor each time.\n \n-sendemail.confirm::\n-\tSets the default for whether to confirm before sending. Must be\n-\tone of 'always', 'never', 'cc', 'compose', or 'auto'. See '--confirm'\n-\tin the previous section for the meaning of these values.\n-\n-\n Author\n ------\n Written by Ryan Anderson <ryan@michonline.com>\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111061","messageId":"1239476908-25944-3-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-2-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 03/10] send-email: Cleanup the usage text and docs a bit","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:21Z","receivedAt":"2009-04-11T19:08:21Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"All usage text lines should be < 80 characters.\n\nA port number in --smtp-server is no longer handled,\nso the suggestion has been removed.\n\n--chain-reply-to doesn't take an argument.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n Documentation/git-send-email.txt |   17 +++++++------\n git-send-email.perl              |   47 +++++++++++++++++++++-----------------\n 2 files changed, 35 insertions(+), 29 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 7cdbdd6..12845d6 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -77,8 +77,9 @@ Missing From or In-Reply-To headers will be prompted for.\n \tthe value GIT_COMMITTER_IDENT, as returned by \"git var -l\".\n \tThe user will still be prompted to confirm this entry.\n \n---in-reply-to=<identifier>::\n-\tSpecify the contents of the first In-Reply-To header.\n+--in-reply-to=<message-id>::\n+\tSpecify the contents of the first In-Reply-To header;\n+\tinclude the angle brackets '<' and '>'.\n \tSubsequent emails will refer to the previous email\n \tinstead of this if --chain-reply-to is set (the default)\n \tOnly necessary if --compose is also set.  If --compose\n@@ -109,7 +110,7 @@ Sending\n \tthe 'sendemail.envelopesender' configuration variable; if that is\n \tunspecified, choosing the envelope sender is left to your MTA.\n \n---smtp-encryption=<encryption>::\n+--smtp-encryption=<type>::\n \tSpecify the encryption to use, either 'ssl' or 'tls'.  Any other\n \tvalue reverts to plain SMTP.  Default is the value of\n \t'sendemail.smtpencryption'.\n@@ -159,7 +160,7 @@ Automating\n \tOutput of this command must be single email address per line.\n \tDefault is the value of 'sendemail.cccmd' configuration value.\n \n---[no-]chain-reply-to=<identifier>::\n+--[no-]chain-reply-to::\n \tIf this is set, each email will be sent as a reply to the previous\n \temail sent.  If disabled with \"--no-chain-reply-to\", all emails after\n \tthe first will be sent as replies to the first email sent.  When using\n@@ -167,11 +168,11 @@ Automating\n \tentire patch series. Default is the value of the 'sendemail.chainreplyto'\n \tconfiguration value; if that is unspecified, default to --chain-reply-to.\n \n---identity=<identity>::\n+--identity=<id>::\n \tA configuration identity. When given, causes values in the\n-\t'sendemail.<identity>' subsection to take precedence over\n+\t'sendemail.<id>' subsection to take precedence over\n \tvalues in the 'sendemail' section. The default identity is\n-\tthe value of 'sendemail.identity'.\n+\tthe value of the 'sendemail.identity' configuration variable.\n \n --[no-]signed-off-by-cc::\n \tIf this is set, add emails found in Signed-off-by: or Cc: lines to the\n@@ -215,7 +216,7 @@ specified, as well as 'body' if --no-signed-off-cc is specified.\n Administering\n ~~~~~~~~~~~~~\n \n---confirm=<mode>::\n+--confirm=<when>::\n \tConfirm just before sending:\n +\n --\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex 172b53c..fb3e712 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -42,46 +42,51 @@ package main;\n \n \n sub usage {\n+\n+\t# All printed lines should be less than 80 characters.\n+\n \tprint <<EOT;\n git send-email [options] <file | directory | rev-list options >\n \n   Composing:\n-    --from                  <str>  * Email From:\n-    --to                    <str>  * Email To:\n-    --cc                    <str>  * Email Cc:\n-    --bcc                   <str>  * Email Bcc:\n-    --subject               <str>  * Email \"Subject:\"\n-    --in-reply-to           <str>  * Email \"In-Reply-To:\"\n-    --annotate                     * Review each patch that will be sent in an editor.\n+    --from              <address>  * Email From:\n+    --to                <address>  * Email To:\n+    --cc                <address>  * Email Cc:\n+    --bcc               <address>  * Email Bcc:\n+    --subject            <string>  * Email \"Subject:\"\n+    --in-reply-to    <message-id>  * Email \"In-Reply-To:\"; include '<' and '>'.\n+    --annotate                     * Review each patch that will be sent in\n+                                     an editor.\n     --compose                      * Open an editor for introduction.\n \n   Sending:\n-    --envelope-sender       <str>  * Email envelope sender.\n-    --smtp-server       <str:int>  * Outgoing SMTP server to use. The port\n-                                     is optional. Default 'localhost'.\n-    --smtp-server-port      <int>  * Outgoing SMTP server port.\n-    --smtp-user             <str>  * Username for SMTP-AUTH.\n-    --smtp-pass             <str>  * Password for SMTP-AUTH; not necessary.\n-    --smtp-encryption       <str>  * tls or ssl; anything else disables.\n+    --envelope-sender   <address>  * Email envelope sender.\n+    --smtp-server          <host>  * Outgoing SMTP server to use.\n+    --smtp-server-port     <port>  * Outgoing SMTP server port.\n+    --smtp-user        <username>  * Username for SMTP-AUTH.\n+    --smtp-pass       [<password>] * Password for SMTP-AUTH; not necessary.\n+    --smtp-encryption      <type>  * tls or ssl; anything else disables.\n     --smtp-ssl                     * Deprecated. Use '--smtp-encryption ssl'.\n \n   Automating:\n-    --identity              <str>  * Use the sendemail.<id> options.\n-    --cc-cmd                <str>  * Email Cc: via `<str> \\$patch_path`\n-    --suppress-cc           <str>  * author, self, sob, cc, cccmd, body, bodycc, all.\n-    --[no-]signed-off-by-cc        * Send to Signed-off-by: addresses. Default on.\n+    --identity               <id>  * Use the sendemail.<id> options.\n+    --cc-cmd            <command>  * Email Cc: via `<command> \\$patch_path`\n+    --suppress-cc      <category>  * author, self, sob, cc, cccmd, body,\n+                                     bodycc, all.\n+    --[no-]signed-off-by-cc        * Send to Signed-off-by: addresses.\n+                                     Default on.\n     --[no-]suppress-from           * Send to self. Default off.\n     --[no-]chain-reply-to          * Chain In-Reply-To: fields. Default on.\n     --[no-]thread                  * Use In-Reply-To: field. Default on.\n \n   Administering:\n-    --confirm               <str>  * Confirm recipients before sending;\n+    --confirm              <when>  * Confirm recipients before sending;\n                                      auto, cc, compose, always, or never.\n     --quiet                        * Output one line of info per email.\n     --dry-run                      * Don't actually send the emails.\n     --[no-]validate                * Perform patch sanity checks. Default on.\n-    --[no-]format-patch            * understand any non optional arguments as\n-                                     `git format-patch` ones.\n+    --[no-]format-patch            * Understand any non-optional arguments as\n+                                     `git format-patch' arguments.\n \n EOT\n \texit(1);\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111062","messageId":"1239476908-25944-4-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-3-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 04/10] send-email: --smtp-server-port should take an integer","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:22Z","receivedAt":"2009-04-11T19:08:22Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Signed-off-by: Michael Witten <mfwitten@gmail.com>\n---\n git-send-email.perl |    2 +-\n 1 files changed, 1 insertions(+), 1 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex fb3e712..b689cc7 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -253,7 +253,7 @@ my $rc = GetOptions(\"sender|from=s\" => \\$sender,\n \t\t    \"bcc=s\" => \\@bcclist,\n \t\t    \"chain-reply-to!\" => \\$chain_reply_to,\n \t\t    \"smtp-server=s\" => \\$smtp_server,\n-\t\t    \"smtp-server-port=s\" => \\$smtp_server_port,\n+\t\t    \"smtp-server-port=i\" => \\$smtp_server_port,\n \t\t    \"smtp-user=s\" => \\$smtp_authuser,\n \t\t    \"smtp-pass:s\" => \\$smtp_authpass,\n \t\t    \"smtp-ssl\" => sub { $smtp_encryption = 'ssl' },\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111063","messageId":"1239476908-25944-5-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-4-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 05/10] send-email: Handle \"GIT:\" rather than \"GIT: \" during --compose","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:23Z","receivedAt":"2009-04-11T19:08:23Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"This should make things a little more robust in terms of user input;\nbefore, even the program got it wrong by outputting a line with only\n\"GIT:\", which was left in place as a header, because there would be\nno following space character.\n\nAlso, I cleaned up get_patch_subject().\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n git-send-email.perl |   23 ++++++++++++-----------\n 1 files changed, 12 insertions(+), 11 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex b689cc7..502f5af 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -507,15 +507,16 @@ if (@files) {\n }\n \n sub get_patch_subject($) {\n-\tmy $fn = shift;\n-\topen (my $fh, '<', $fn);\n-\twhile (my $line = <$fh>) {\n-\t\tnext unless ($line =~ /^Subject: (.*)$/);\n-\t\tclose $fh;\n-\t\treturn \"GIT: $1\\n\";\n+\n+\tmy $patch = shift;\n+\topen (my $fh, '<', $patch);\n+\n+\twhile (<$fh>) {\n+\t\tnext unless (/^Subject: (.*)$/);\n+\t\treturn $1;\n \t}\n-\tclose $fh;\n-\tdie \"No subject line in $fn ?\";\n+\n+\tdie \"'Subject:' line expected in '$patch'\";\n }\n \n if ($compose) {\n@@ -534,7 +535,7 @@ if ($compose) {\n \n \tprint C <<EOT;\n From $tpl_sender # This line is ignored.\n-GIT: Lines beginning in \"GIT: \" will be removed.\n+GIT: Lines beginning in \"GIT:\" will be removed.\n GIT: Consider including an overall diffstat or table of contents\n GIT: for the patch you are writing.\n GIT:\n@@ -545,7 +546,7 @@ In-Reply-To: $tpl_reply_to\n \n EOT\n \tfor my $f (@files) {\n-\t\tprint C get_patch_subject($f);\n+\t\tprint C \"GIT: \", get_patch_subject($f), \"\\n\";\n \t}\n \tclose(C);\n \n@@ -567,7 +568,7 @@ EOT\n \tmy $in_body = 0;\n \tmy $summary_empty = 1;\n \twhile(<C>) {\n-\t\tnext if m/^GIT: /;\n+\t\tnext if m/^GIT:/;\n \t\tif ($in_body) {\n \t\t\t$summary_empty = 0 unless (/^\\n$/);\n \t\t} elsif (/^\\n$/) {\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111064","messageId":"1239476908-25944-6-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-5-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 06/10] send-email: References: should only reference what is actually sent","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:24Z","receivedAt":"2009-04-11T19:08:24Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"If someone responded with a negative (n|no) to the confirmation,\nthen the Message-ID of the discarded email is no longer used\nin the References: header of subsequent emails.\n\nConsequently, send_message() now returns 1 if the message was\nsent and 0 otherwise.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n git-send-email.perl |   14 ++++++++++----\n 1 files changed, 10 insertions(+), 4 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex 502f5af..d90c76e 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -802,6 +802,10 @@ sub sanitize_address\n \n }\n \n+# returns 1 of the message was sent, 0 otherwise.\n+# In actuality, the whole program dies when a there\n+# is an error sending a message.\n+\n sub send_message\n {\n \tmy @recipients = unique_email_list(@to);\n@@ -870,7 +874,7 @@ X-Mailer: git-send-email $gitversion\n \t\t         default => $ask_default);\n \t\tdie \"Send this email reply required\" unless defined $_;\n \t\tif (/^n/i) {\n-\t\t\treturn;\n+\t\t\treturn 0;\n \t\t} elsif (/^q/i) {\n \t\t\tcleanup_compose_files();\n \t\t\texit(0);\n@@ -951,7 +955,7 @@ X-Mailer: git-send-email $gitversion\n \t\t$smtp->data or die $smtp->message;\n \t\t$smtp->datasend(\"$header\\n$message\") or die $smtp->message;\n \t\t$smtp->dataend() or die $smtp->message;\n-\t\t$smtp->ok or die \"Failed to send $subject\\n\".$smtp->message;\n+\t\t$smtp->code =~ /250|200/ or die \"Failed to send $subject\\n\".$smtp->message;\n \t}\n \tif ($quiet) {\n \t\tprintf (($dry_run ? \"Dry-\" : \"\").\"Sent %s\\n\", $subject);\n@@ -972,6 +976,8 @@ X-Mailer: git-send-email $gitversion\n \t\t\tprint \"Result: OK\\n\";\n \t\t}\n \t}\n+\n+\treturn 1;\n }\n \n $reply_to = $initial_reply_to;\n@@ -1132,10 +1138,10 @@ foreach my $t (@files) {\n \n \t@cc = (@initial_cc, @cc);\n \n-\tsend_message();\n+\tmy $message_was_sent = send_message();\n \n \t# set up for the next message\n-\tif ($chain_reply_to || !defined $reply_to || length($reply_to) == 0) {\n+\tif ($message_was_sent and $chain_reply_to || not defined $reply_to || length($reply_to) == 0) {\n \t\t$reply_to = $message_id;\n \t\tif (length $references > 0) {\n \t\t\t$references .= \"\\n $message_id\";\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111065","messageId":"1239476908-25944-7-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-6-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 07/10] send-email: Remove horrible mix of tabs and spaces","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:25Z","receivedAt":"2009-04-11T19:08:25Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"For the most part, I ran a search for all the lines\nthat match:\n\n    ^[\\t]*[ ]+\n\nand then I manually replaced the offending text with\nan appropriate number of tabs.\n\nWhile scanning through the file, I also tried to format\nsome of the code so as to obviate future mixing; I also\nfixed one horrendously egregious section of code, where\nsomeone was trying to be unnecessarily compact.\n\nCurrently, no lines match the following:\n\n    [\\t]+[ ]+\n    [ ]+[\\t]+\n\nSo, it should be reasonably clean.\n\nThe whole file is still horrendous.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n git-send-email.perl |  278 +++++++++++++++++++++++++++++++--------------------\n 1 files changed, 168 insertions(+), 110 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex d90c76e..4f0462f 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -16,6 +16,14 @@\n #    and second line is the subject of the message.\n #\n \n+## WARNING! ACHTUNG! ATTENTION! ADVERTENCIA!\n+##   Currently, this file uses tabs (like the rest of git source) to\n+##   delineate code structure. Do NOT under any circumstances mix tabs\n+##   and spaces across lines that share a relationship in terms of layout.\n+##   In fact, it would currently be best to use only tabs, so please set\n+##   your editor(s) accordingly. This code is already trashy enough. Please\n+##   don't make it worse.\n+\n use strict;\n use warnings;\n use Term::ReadLine;\n@@ -116,19 +124,20 @@ sub format_2822_time {\n \t\tdie (\"local time offset greater than or equal to 24 hours\\n\");\n \t}\n \n-\treturn sprintf(\"%s, %2d %s %d %02d:%02d:%02d %s%02d%02d\",\n-\t\t       qw(Sun Mon Tue Wed Thu Fri Sat)[$localtm[6]],\n-\t\t       $localtm[3],\n-\t\t       qw(Jan Feb Mar Apr May Jun\n-\t\t\t  Jul Aug Sep Oct Nov Dec)[$localtm[4]],\n-\t\t       $localtm[5]+1900,\n-\t\t       $localtm[2],\n-\t\t       $localtm[1],\n-\t\t       $localtm[0],\n-\t\t       ($offset >= 0) ? '+' : '-',\n-\t\t       abs($offhour),\n-\t\t       $offmin,\n-\t\t       );\n+\treturn sprintf(\n+\t\t\"%s, %2d %s %d %02d:%02d:%02d %s%02d%02d\",\n+\t\tqw(Sun Mon Tue Wed Thu Fri Sat)[$localtm[6]],\n+\t\t$localtm[3],\n+\t\tqw(Jan Feb Mar Apr May Jun\n+\t\tJul Aug Sep Oct Nov Dec)[$localtm[4]],\n+\t\t$localtm[5]+1900,\n+\t\t$localtm[2],\n+\t\t$localtm[1],\n+\t\t$localtm[0],\n+\t\t($offset >= 0) ? '+' : '-',\n+\t\tabs($offhour),\n+\t\t$offmin,\n+\t);\n }\n \n my $have_email_valid = eval { require Email::Valid; 1 };\n@@ -192,29 +201,29 @@ my ($validate, $confirm);\n my (@suppress_cc);\n \n my %config_bool_settings = (\n-    \"thread\" => [\\$thread, 1],\n-    \"chainreplyto\" => [\\$chain_reply_to, 1],\n-    \"suppressfrom\" => [\\$suppress_from, undef],\n-    \"signedoffbycc\" => [\\$signed_off_by_cc, undef],\n-    \"signedoffcc\" => [\\$signed_off_by_cc, undef],      # Deprecated\n-    \"validate\" => [\\$validate, 1],\n+\t\"thread\" => [\\$thread, 1],\n+\t\"chainreplyto\" => [\\$chain_reply_to, 1],\n+\t\"suppressfrom\" => [\\$suppress_from, undef],\n+\t\"signedoffbycc\" => [\\$signed_off_by_cc, undef],\n+\t\"signedoffcc\" => [\\$signed_off_by_cc, undef],      # Deprecated\n+\t\"validate\" => [\\$validate, 1],\n );\n \n my %config_settings = (\n-    \"smtpserver\" => \\$smtp_server,\n-    \"smtpserverport\" => \\$smtp_server_port,\n-    \"smtpuser\" => \\$smtp_authuser,\n-    \"smtppass\" => \\$smtp_authpass,\n-    \"to\" => \\@to,\n-    \"cc\" => \\@initial_cc,\n-    \"cccmd\" => \\$cc_cmd,\n-    \"aliasfiletype\" => \\$aliasfiletype,\n-    \"bcc\" => \\@bcclist,\n-    \"aliasesfile\" => \\@alias_files,\n-    \"suppresscc\" => \\@suppress_cc,\n-    \"envelopesender\" => \\$envelope_sender,\n-    \"multiedit\" => \\$multiedit,\n-    \"confirm\"   => \\$confirm,\n+\t\"smtpserver\" => \\$smtp_server,\n+\t\"smtpserverport\" => \\$smtp_server_port,\n+\t\"smtpuser\" => \\$smtp_authuser,\n+\t\"smtppass\" => \\$smtp_authpass,\n+\t\"to\" => \\@to,\n+\t\"cc\" => \\@initial_cc,\n+\t\"cccmd\" => \\$cc_cmd,\n+\t\"aliasfiletype\" => \\$aliasfiletype,\n+\t\"bcc\" => \\@bcclist,\n+\t\"aliasesfile\" => \\@alias_files,\n+\t\"suppresscc\" => \\@suppress_cc,\n+\t\"envelopesender\" => \\$envelope_sender,\n+\t\"multiedit\" => \\$multiedit,\n+\t\"confirm\"   => \\$confirm,\n );\n \n # Handle Uncouth Termination\n@@ -245,37 +254,38 @@ $SIG{INT}  = \\&signal_handler;\n # Begin by accumulating all the variables (defined above), that we will end up\n # needing, first, from the command line:\n \n-my $rc = GetOptions(\"sender|from=s\" => \\$sender,\n-                    \"in-reply-to=s\" => \\$initial_reply_to,\n-\t\t    \"subject=s\" => \\$initial_subject,\n-\t\t    \"to=s\" => \\@to,\n-\t\t    \"cc=s\" => \\@initial_cc,\n-\t\t    \"bcc=s\" => \\@bcclist,\n-\t\t    \"chain-reply-to!\" => \\$chain_reply_to,\n-\t\t    \"smtp-server=s\" => \\$smtp_server,\n-\t\t    \"smtp-server-port=i\" => \\$smtp_server_port,\n-\t\t    \"smtp-user=s\" => \\$smtp_authuser,\n-\t\t    \"smtp-pass:s\" => \\$smtp_authpass,\n-\t\t    \"smtp-ssl\" => sub { $smtp_encryption = 'ssl' },\n-\t\t    \"smtp-encryption=s\" => \\$smtp_encryption,\n-\t\t    \"identity=s\" => \\$identity,\n-\t\t    \"annotate\" => \\$annotate,\n-\t\t    \"compose\" => \\$compose,\n-\t\t    \"quiet\" => \\$quiet,\n-\t\t    \"cc-cmd=s\" => \\$cc_cmd,\n-\t\t    \"suppress-from!\" => \\$suppress_from,\n-\t\t    \"suppress-cc=s\" => \\@suppress_cc,\n-\t\t    \"signed-off-cc|signed-off-by-cc!\" => \\$signed_off_by_cc,\n-\t\t    \"confirm=s\" => \\$confirm,\n-\t\t    \"dry-run\" => \\$dry_run,\n-\t\t    \"envelope-sender=s\" => \\$envelope_sender,\n-\t\t    \"thread!\" => \\$thread,\n-\t\t    \"validate!\" => \\$validate,\n-\t\t    \"format-patch!\" => \\$format_patch,\n-\t );\n+my $rc = GetOptions(\n+\t\"sender|from=s\" => \\$sender,\n+\t\"in-reply-to=s\" => \\$initial_reply_to,\n+\t\"subject=s\" => \\$initial_subject,\n+\t\"to=s\" => \\@to,\n+\t\"cc=s\" => \\@initial_cc,\n+\t\"bcc=s\" => \\@bcclist,\n+\t\"chain-reply-to!\" => \\$chain_reply_to,\n+\t\"smtp-server=s\" => \\$smtp_server,\n+\t\"smtp-server-port=i\" => \\$smtp_server_port,\n+\t\"smtp-user=s\" => \\$smtp_authuser,\n+\t\"smtp-pass:s\" => \\$smtp_authpass,\n+\t\"smtp-ssl\" => sub { $smtp_encryption = 'ssl' },\n+\t\"smtp-encryption=s\" => \\$smtp_encryption,\n+\t\"identity=s\" => \\$identity,\n+\t\"annotate\" => \\$annotate,\n+\t\"compose\" => \\$compose,\n+\t\"quiet\" => \\$quiet,\n+\t\"cc-cmd=s\" => \\$cc_cmd,\n+\t\"suppress-from!\" => \\$suppress_from,\n+\t\"suppress-cc=s\" => \\@suppress_cc,\n+\t\"signed-off-cc|signed-off-by-cc!\" => \\$signed_off_by_cc,\n+\t\"confirm=s\" => \\$confirm,\n+\t\"dry-run\" => \\$dry_run,\n+\t\"envelope-sender=s\" => \\$envelope_sender,\n+\t\"thread!\" => \\$thread,\n+\t\"validate!\" => \\$validate,\n+\t\"format-patch!\" => \\$format_patch,\n+);\n \n unless ($rc) {\n-    usage();\n+\tusage();\n }\n \n die \"Cannot run git format-patch from outside a repository\\n\"\n@@ -404,29 +414,55 @@ sub split_addrs {\n my %aliases;\n my %parse_alias = (\n \t# multiline formats can be supported in the future\n-\tmutt => sub { my $fh = shift; while (<$fh>) {\n-\t\tif (/^\\s*alias\\s+(\\S+)\\s+(.*)$/) {\n-\t\t\tmy ($alias, $addr) = ($1, $2);\n-\t\t\t$addr =~ s/#.*$//; # mutt allows # comments\n-\t\t\t # commas delimit multiple addresses\n-\t\t\t$aliases{$alias} = [ split_addrs($addr) ];\n-\t\t}}},\n-\tmailrc => sub { my $fh = shift; while (<$fh>) {\n-\t\tif (/^alias\\s+(\\S+)\\s+(.*)$/) {\n-\t\t\t# spaces delimit multiple addresses\n-\t\t\t$aliases{$1} = [ split(/\\s+/, $2) ];\n-\t\t}}},\n-\tpine => sub { my $fh = shift; my $f='\\t[^\\t]*';\n-\t        for (my $x = ''; defined($x); $x = $_) {\n+\tmutt => sub {\n+\n+\t\tmy $fh = shift;\n+\n+\t\twhile (<$fh>) {\n+\t\t\tif (/^\\s*alias\\s+(\\S+)\\s+(.*)$/) {\n+\t\t\t\tmy ($alias, $addr) = ($1, $2);\n+\t\t\t\t$addr =~ s/#.*$//; # mutt allows # comments\n+\t\t\t\t# commas delimit multiple addresses\n+\t\t\t\t$aliases{$alias} = [ split_addrs($addr) ];\n+\t\t\t}\n+\t\t}\n+\t},\n+\n+\tmailrc => sub {\n+\n+\t\tmy $fh = shift;\n+\n+\t\twhile (<$fh>) {\n+\t\t\tif (/^alias\\s+(\\S+)\\s+(.*)$/) {\n+\t\t\t\t# spaces delimit multiple addresses\n+\t\t\t\t$aliases{$1} = [ split(/\\s+/, $2) ];\n+\t\t\t}\n+\t\t}\n+\t},\n+\n+\tpine => sub {\n+\n+\t\tmy $fh = shift;\n+\t\tmy $f='\\t[^\\t]*';\n+\n+\t\tfor (my $x = ''; defined($x); $x = $_) {\n \t\t\tchomp $x;\n-\t\t        $x .= $1 while(defined($_ = <$fh>) && /^ +(.*)$/);\n+\t\t\t$x .= $1 while(defined($_ = <$fh>) && /^ +(.*)$/);\n \t\t\t$x =~ /^(\\S+)$f\\t\\(?([^\\t]+?)\\)?(:?$f){0,2}$/ or next;\n \t\t\t$aliases{$1} = [ split_addrs($2) ];\n-\t\t}},\n-\tgnus => sub { my $fh = shift; while (<$fh>) {\n-\t\tif (/\\(define-mail-alias\\s+\"(\\S+?)\"\\s+\"(\\S+?)\"\\)/) {\n-\t\t\t$aliases{$1} = [ $2 ];\n-\t\t}}}\n+\t\t}\n+\t},\n+\n+\tgnus => sub {\n+\n+\t\tmy $fh = shift;\n+\n+\t\twhile (<$fh>) {\n+\t\t\tif (/\\(define-mail-alias\\s+\"(\\S+?)\"\\s+\"(\\S+?)\"\\)/) {\n+\t\t\t\t$aliases{$1} = [ $2 ];\n+\t\t\t}\n+\t\t}\n+\t}\n );\n \n if (@alias_files and $aliasfiletype and defined $parse_alias{$aliasfiletype}) {\n@@ -574,10 +610,11 @@ EOT\n \t\t} elsif (/^\\n$/) {\n \t\t\t$in_body = 1;\n \t\t\tif ($need_8bit_cte) {\n-\t\t\t\tprint C2 \"MIME-Version: 1.0\\n\",\n-\t\t\t\t\t \"Content-Type: text/plain; \",\n-\t\t\t\t\t   \"charset=utf-8\\n\",\n-\t\t\t\t\t \"Content-Transfer-Encoding: 8bit\\n\";\n+\t\t\t\tprint C2\n+\t\t\t\t\t\"MIME-Version: 1.0\\n\",\n+\t\t\t\t\t\"Content-Type: text/plain; \",\n+\t\t\t\t\t\"charset=utf-8\\n\",\n+\t\t\t\t\t\"Content-Transfer-Encoding: 8bit\\n\";\n \t\t\t}\n \t\t} elsif (/^MIME-Version:/i) {\n \t\t\t$need_8bit_cte = 0;\n@@ -586,8 +623,8 @@ EOT\n \t\t\tmy $subject = $initial_subject;\n \t\t\t$_ = \"Subject: \" .\n \t\t\t\t($subject =~ /[^[:ascii:]]/ ?\n-\t\t\t\t quote_rfc2047($subject) :\n-\t\t\t\t $subject) .\n+\t\t\t\tquote_rfc2047($subject) :\n+\t\t\t\t$subject) .\n \t\t\t\t\"\\n\";\n \t\t} elsif (/^In-Reply-To:\\s*(.+)\\s*$/i) {\n \t\t\t$initial_reply_to = $1;\n@@ -619,8 +656,10 @@ sub ask {\n \tmy $resp;\n \tmy $i = 0;\n \treturn defined $default ? $default : undef\n-\t\tunless defined $term->IN and defined fileno($term->IN) and\n-\t\t       defined $term->OUT and defined fileno($term->OUT);\n+\t\tunless defined $term->IN\n+\t\t\tand defined fileno($term->IN)\n+\t\t\tand defined $term->OUT\n+\t\t\tand defined fileno($term->OUT);\n \twhile ($i++ < 10) {\n \t\t$resp = $term->readline($prompt);\n \t\tif (!defined $resp) { # EOF\n@@ -640,8 +679,12 @@ sub ask {\n my $prompting = 0;\n if (!defined $sender) {\n \t$sender = $repoauthor || $repocommitter || '';\n-\t$sender = ask(\"Who should the emails appear to be from? [$sender] \",\n-\t              default => $sender);\n+\n+\t$sender = ask(\n+\t\t\"Who should the emails appear to be from? [$sender] \",\n+\t\tdefault => $sender\n+\t);\n+\n \tprint \"Emails will be sent from: \", $sender, \"\\n\";\n \t$prompting++;\n }\n@@ -669,7 +712,8 @@ sub expand_aliases {\n \n if ($thread && !defined $initial_reply_to && $prompting) {\n \t$initial_reply_to = ask(\n-\t\t\"Message-ID to be used as In-Reply-To for the first email? \");\n+\t\t\"Message-ID to be used as In-Reply-To for the first email? \"\n+\t);\n }\n if (defined $initial_reply_to) {\n \t$initial_reply_to =~ s/^\\s*<?//;\n@@ -809,18 +853,22 @@ sub sanitize_address\n sub send_message\n {\n \tmy @recipients = unique_email_list(@to);\n-\t@cc = (grep { my $cc = extract_valid_address($_);\n-\t\t      not grep { $cc eq $_ } @recipients\n-\t\t    }\n-\t       map { sanitize_address($_) }\n-\t       @cc);\n+\n+\t@cc = (grep\n+\t\t{\n+\t\t\tmy $cc = extract_valid_address($_);\n+\t\t\tnot grep { $cc eq $_ } @recipients\n+\t\t}\n+\t\tmap { sanitize_address($_) } @cc\n+\t);\n+\n \tmy $to = join (\",\\n\\t\", @recipients);\n \t@recipients = unique_email_list(@recipients,@cc,@bcclist);\n \t@recipients = (map { extract_valid_address($_) } @recipients);\n \tmy $date = format_2822_time($time++);\n \tmy $gitversion = '@@GIT_VERSION@@';\n \tif ($gitversion =~ m/..GIT_VERSION../) {\n-\t    $gitversion = Git::version();\n+\t\t$gitversion = Git::version();\n \t}\n \n \tmy $cc = join(\", \", unique_email_list(@cc));\n@@ -869,9 +917,13 @@ X-Mailer: git-send-email $gitversion\n \t\t\tprint \"    To retain the current behavior, but squelch this message,\\n\";\n \t\t\tprint \"    run 'git config --global sendemail.confirm auto'.\\n\\n\";\n \t\t}\n-\t\t$_ = ask(\"Send this email? ([y]es|[n]o|[q]uit|[a]ll): \",\n-\t\t         valid_re => qr/^(?:yes|y|no|n|quit|q|all|a)/i,\n-\t\t         default => $ask_default);\n+\n+\t\t$_ = ask(\n+\t\t\t\"Send this email? ([y]es|[n]o|[q]uit|[a]ll): \",\n+\t\t\tvalid_re => qr/^(?:yes|y|no|n|quit|q|all|a)/i,\n+\t\t\tdefault => $ask_default\n+\t\t);\n+\n \t\tdie \"Send this email reply required\" unless defined $_;\n \t\tif (/^n/i) {\n \t\t\treturn 0;\n@@ -906,9 +958,13 @@ X-Mailer: git-send-email $gitversion\n \t\t}\n \t\telse {\n \t\t\trequire Net::SMTP;\n-\t\t\t$smtp ||= Net::SMTP->new((defined $smtp_server_port)\n-\t\t\t\t\t\t ? \"$smtp_server:$smtp_server_port\"\n-\t\t\t\t\t\t : $smtp_server);\n+\n+\t\t\t$smtp ||= Net::SMTP->new(\n+\t\t\t\t(defined $smtp_server_port)\n+\t\t\t\t\t? \"$smtp_server:$smtp_server_port\"\n+\t\t\t\t\t: $smtp_server\n+\t\t\t);\n+\n \t\t\tif ($smtp_encryption eq 'tls') {\n \t\t\t\trequire Net::SMTP::SSL;\n \t\t\t\t$smtp->command('STARTTLS');\n@@ -1005,7 +1061,7 @@ foreach my $t (@files) {\n \t\t\tchomp($header[$#header]);\n \t\t\ts/^\\s+/ /;\n \t\t\t$header[$#header] .= $_;\n-\t    } else {\n+\t\t} else {\n \t\t\tpush(@header, $_);\n \t\t}\n \t}\n@@ -1123,9 +1179,9 @@ foreach my $t (@files) {\n \t\t\t}\n \t\t\telse {\n \t\t\t\tpush @xh,\n-\t\t\t\t  'MIME-Version: 1.0',\n-\t\t\t\t  \"Content-Type: text/plain; charset=$author_encoding\",\n-\t\t\t\t  'Content-Transfer-Encoding: 8bit';\n+\t\t\t\t\t'MIME-Version: 1.0',\n+\t\t\t\t\t\"Content-Type: text/plain; charset=$author_encoding\",\n+\t\t\t\t\t'Content-Transfer-Encoding: 8bit';\n \t\t\t}\n \t\t}\n \t}\n@@ -1133,7 +1189,9 @@ foreach my $t (@files) {\n \t$needs_confirm = (\n \t\t$confirm eq \"always\" or\n \t\t($confirm =~ /^(?:auto|cc)$/ && @cc) or\n-\t\t($confirm =~ /^(?:auto|compose)$/ && $compose && $message_num == 1));\n+\t\t($confirm =~ /^(?:auto|compose)$/ && $compose && $message_num == 1)\n+\t);\n+\n \t$needs_confirm = \"inform\" if ($needs_confirm && $confirm_unconfigured && @cc);\n \n \t@cc = (@initial_cc, @cc);\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111066","messageId":"1239476908-25944-8-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-7-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 08/10] send-email: Add --sleep for email throttling","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:26Z","receivedAt":"2009-04-11T19:08:26Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"The --sleep option provides a means for specifying that there\nshould be a certain number of seconds of delay after sending\na certain number of emails; see Documentation/git-send-email.txt\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n Documentation/git-send-email.txt |   30 +++++++++++++++\n git-send-email.perl              |   74 +++++++++++++++++++++++++++++++++++---\n 2 files changed, 99 insertions(+), 5 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 12845d6..f0c2e7b 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -168,6 +168,36 @@ Automating\n \tentire patch series. Default is the value of the 'sendemail.chainreplyto'\n \tconfiguration value; if that is unspecified, default to --chain-reply-to.\n \n+--sleep=<seconds>[,<burst>]::\n+\tThis option specfies that send-email should sleep for <seconds>\n+\tafter sending <burst> messages as quickly as possible; <seconds>\n+\tshould be an integer >= 0 and <burst> should be an integer >= 1.\n+\tThis mode of operation attacks 2 problems: email throttling and\n+\tarrival disorder. Default is the value of the 'sendemail.sleep'\n+\tconfiguration variable, or '0' if that does not exist.\n++\n+By default, send-email tries to send one patch per email as quickly as\n+possible. Unfortunately, some email services restrict a user by refusing\n+to send more than some maximum number of email messages, M, in a given\n+period of seconds, S. This can be troublesome if the patch series has\n+more than M patches, because the server will ultimately refuse to send\n+some of them. In this case, simply pass '--sleep=S,M' or '--sleep S,M'\n+or set sendemail.sleep to 'S,M'.\n++\n+Moreover, the emails often arrive at the final destination out of order;\n+though send-email manipulates the date fields and usually chains subsequent\n+emails via the In-Reply-To headers, some mail viewers nevertheless insist\n+on presenting them by order of arrival. This may be mitigated by using\n+something like '--sleep 60' (the equivalent of '--sleep 60,1'), so that\n+there is a 60 second delay between sending each patch.\n++\n+*Note*: Because of varying routes and batching schemes, there is no delay\n+that can guarantee the correct arrival order. Obviously, one solution is to\n+choose an obscenely large number, so be prepared to run send-email in the\n+background. Of course, spreading emails across time makes it more likely\n+that unrelated email messages arrive between patches. Therefore, send-email\n+warns you if both --sleep and --no-chain-reply-to are used.\n+\n --identity=<id>::\n \tA configuration identity. When given, causes values in the\n \t'sendemail.<id>' subsection to take precedence over\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex 4f0462f..c26a1b5 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -77,6 +77,7 @@ git send-email [options] <file | directory | rev-list options >\n     --smtp-ssl                     * Deprecated. Use '--smtp-encryption ssl'.\n \n   Automating:\n+    --sleep      <secs>[,<burst>]  * Delay <secs> every <burst> email(s).\n     --identity               <id>  * Use the sendemail.<id> options.\n     --cc-cmd            <command>  * Email Cc: via `<command> \\$patch_path`\n     --suppress-cc      <category>  * author, self, sob, cc, cccmd, body,\n@@ -194,7 +195,7 @@ sub do_edit {\n }\n \n # Variables with corresponding config settings\n-my ($thread, $chain_reply_to, $suppress_from, $signed_off_by_cc, $cc_cmd);\n+my ($sleep, $thread, $chain_reply_to, $suppress_from, $signed_off_by_cc, $cc_cmd);\n my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_encryption);\n my ($identity, $aliasfiletype, @alias_files, @smtp_host_parts);\n my ($validate, $confirm);\n@@ -210,6 +211,7 @@ my %config_bool_settings = (\n );\n \n my %config_settings = (\n+\t\"sleep\" => \\$sleep,\n \t\"smtpserver\" => \\$smtp_server,\n \t\"smtpserverport\" => \\$smtp_server_port,\n \t\"smtpuser\" => \\$smtp_authuser,\n@@ -262,6 +264,7 @@ my $rc = GetOptions(\n \t\"cc=s\" => \\@initial_cc,\n \t\"bcc=s\" => \\@bcclist,\n \t\"chain-reply-to!\" => \\$chain_reply_to,\n+\t\"sleep=s\" => \\$sleep,\n \t\"smtp-server=s\" => \\$smtp_server,\n \t\"smtp-server-port=i\" => \\$smtp_server_port,\n \t\"smtp-user=s\" => \\$smtp_authuser,\n@@ -334,6 +337,43 @@ foreach my $setting (values %config_bool_settings) {\n \t${$setting->[0]} = $setting->[1] unless (defined (${$setting->[0]}));\n }\n \n+#### Parse input\n+\n+my ($sleep_seconds, $sleep_burst);\n+\n+if (defined $sleep) {{\n+\n+\tunless ($chain_reply_to) {\n+\n+\t\tprint \"Both --sleep and --no-chain-reply-to are in effect.\\n\";\n+\t\tprint \"Therefore, it is much more likely that unrelated\\n\";\n+\t\tprint \"email messages will appear between any 2 of your\\n\";\n+\t\tprint \"patches.\\n\\n\";\n+\n+\t\t$_ = ask(\n+\t\t\t\"How to proceed? ([q]uit | --[s]leep | --no-[c]hain | [n]either | [b]oth): \",\n+\t\t\tvalid_re => qr/^(?:b|s|c|n|q)/i,\n+\t\t\tdefault => 'b'\n+\t\t);\n+\n+\t\t/^b/                                               or\n+\t\t/^s/ and $chain_reply_to = 1                       or\n+\t\t/^c/ and $sleep = undef, last                      or\n+\t\t/^n/ and $chain_reply_to = 1, $sleep = undef, last or\n+\t\t/^q/ and exit;\n+\t}\n+\n+\t$sleep =~ /^(\\d+)(?:,(\\d+))?$/\n+\t\tor  print \"Should be '--sleep=<seconds>[,<burst>]', but got '--sleep=\\\"$sleep\\\"'\\n\"\n+\t\tand exit;\n+\n+\t# Explicitly convert to integers to avoid repeated conversion:\n+\t# (<burst> = 0 is not defined, but let's be nice and absorb it)\n+\n+\t$sleep_seconds = 0+$1;\n+\t$sleep_burst   = $2 ? 0+$2 : 1;\n+}}\n+\n # 'default' encryption is none -- this only prevents a warning\n $smtp_encryption = '' unless (defined $smtp_encryption);\n \n@@ -1041,8 +1081,12 @@ $references = $initial_reply_to || '';\n $subject = $initial_subject;\n $message_num = 0;\n \n-foreach my $t (@files) {\n-\topen(F,\"<\",$t) or die \"can't open file $t\";\n+my $burst_count = $sleep_burst;\n+my $time_of_last_message;\n+\n+for (my $index = 0; $index < @files; $index++) {\n+\tmy $file = $files[$index];\n+\topen(F,\"<\",$file) or die \"can't open file $file\";\n \n \tmy $author = undef;\n \tmy $author_encoding;\n@@ -1151,7 +1195,7 @@ foreach my $t (@files) {\n \tclose F;\n \n \tif (defined $cc_cmd && !$suppress_cc{'cccmd'}) {\n-\t\topen(F, \"$cc_cmd $t |\")\n+\t\topen(F, \"$cc_cmd $file |\")\n \t\t\tor die \"(cc-cmd) Could not execute '$cc_cmd'\";\n \t\twhile(<F>) {\n \t\t\tmy $c = $_;\n@@ -1198,7 +1242,27 @@ foreach my $t (@files) {\n \n \tmy $message_was_sent = send_message();\n \n-\t# set up for the next message\n+\t# Throttle the outgoing rate:\n+\n+\tif ($sleep_seconds && $message_was_sent) {\n+\n+\t\t$time_of_last_message = time;\n+\n+\t\tunless (--$burst_count) {  # unless we can send more\n+\n+\t\t\t$burst_count = $sleep_burst;\n+\n+\t\t\tmy $already_elapsed = time - $time_of_last_message;\n+\n+\t\t\tif ($already_elapsed < $sleep_seconds && $index < $#files) {\n+\t\t\t\tmy $this_long = $sleep_seconds - $already_elapsed;\n+\t\t\t\twhile (($this_long -= sleep $this_long) > 0) {}\n+\t\t\t}\n+\t\t}\n+\t}\n+\n+\t# set up for the next message:\n+\n \tif ($message_was_sent and $chain_reply_to || not defined $reply_to || length($reply_to) == 0) {\n \t\t$reply_to = $message_id;\n \t\tif (length $references > 0) {\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111067","messageId":"1239476908-25944-9-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-8-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 09/10] send-email: Minor cleanup of $smtp_server usage and send_message()","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:27Z","receivedAt":"2009-04-11T19:08:27Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Note that the output has been changed; the server return code\nnow appears after the `(Sendmail|Server):' line, rather than\nafter the headers.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n Documentation/git-send-email.txt |    3 +-\n git-send-email.perl              |   39 +++++++++++++++++++++++--------------\n 2 files changed, 26 insertions(+), 16 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex f0c2e7b..07c831e 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -135,7 +135,8 @@ user is prompted for a password while the input is masked for privacy.\n \tbe specified by the 'sendemail.smtpserver' configuration\n \toption; the built-in default is `/usr/sbin/sendmail` or\n \t`/usr/lib/sendmail` if such program is available, or\n-\t`localhost` otherwise.\n+\t`127.0.0.1` otherwise. Also, if <host> is the empty string,\n+\tthen a built-in default is used.\n \n --smtp-server-port=<port>::\n \tSpecifies a port different from the default port (SMTP\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex c26a1b5..e771720 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -196,7 +196,8 @@ sub do_edit {\n \n # Variables with corresponding config settings\n my ($sleep, $thread, $chain_reply_to, $suppress_from, $signed_off_by_cc, $cc_cmd);\n-my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_encryption);\n+my ($smtp_server, $smtp_server_is_a_command);\n+my ($smtp_server_port, $smtp_authuser, $smtp_encryption);\n my ($identity, $aliasfiletype, @alias_files, @smtp_host_parts);\n my ($validate, $confirm);\n my (@suppress_cc);\n@@ -761,14 +762,18 @@ if (defined $initial_reply_to) {\n \t$initial_reply_to = \"<$initial_reply_to>\" if $initial_reply_to ne '';\n }\n \n-if (!defined $smtp_server) {\n+if (defined $smtp_server and $smtp_server ne '') {\n+\t$smtp_server_is_a_command = ($smtp_server =~ m{^/});\n+} else {\n \tforeach (qw( /usr/sbin/sendmail /usr/lib/sendmail )) {\n \t\tif (-x $_) {\n \t\t\t$smtp_server = $_;\n+\t\t\t$smtp_server_is_a_command = 1;\n \t\t\tlast;\n \t\t}\n \t}\n-\t$smtp_server ||= 'localhost'; # could be 127.0.0.1, too... *shrug*\n+\t$smtp_server_is_a_command = 0;\n+\t$smtp_server ||= '127.0.0.1';\n }\n \n if ($compose && $compose > 0) {\n@@ -977,7 +982,7 @@ X-Mailer: git-send-email $gitversion\n \n \tif ($dry_run) {\n \t\t# We don't want to send the email.\n-\t} elsif ($smtp_server =~ m#^/#) {\n+\t} elsif ($smtp_server_is_a_command) {\n \t\tmy $pid = open my $sm, '|-';\n \t\tdefined $pid or die $!;\n \t\tif (!$pid) {\n@@ -1053,24 +1058,28 @@ X-Mailer: git-send-email $gitversion\n \t\t$smtp->dataend() or die $smtp->message;\n \t\t$smtp->code =~ /250|200/ or die \"Failed to send $subject\\n\".$smtp->message;\n \t}\n+\n+\tprint 'Dry-' if $dry_run;\n+\n \tif ($quiet) {\n-\t\tprintf (($dry_run ? \"Dry-\" : \"\").\"Sent %s\\n\", $subject);\n+\t\tprint \"Sent $subject\\n\";\n \t} else {\n-\t\tprint (($dry_run ? \"Dry-\" : \"\").\"OK. Log says:\\n\");\n-\t\tif ($smtp_server !~ m#^/#) {\n+\t\tprint \"OK. Log says:\\n\";\n+\n+\t\tif ($smtp_server_is_a_command) {\n+\t\t\tprint \"Sendmail: $smtp_server \".join(' ',@sendmail_parameters).\"\\n\";\n+\t\t\tprint \"Result: OK\\n\";\n+\t\t} else {\n \t\t\tprint \"Server: $smtp_server\\n\";\n+\n+\t\t\t$dry_run and print \"Result: OK\\n\" or\n+\t\t\tprint \"Result: \", $smtp->code, ' ', ($smtp->message =~ /\\n([^\\n]+\\n)$/s), \"\\n\";\n+\n \t\t\tprint \"MAIL FROM:<$raw_from>\\n\";\n \t\t\tprint \"RCPT TO:\".join(',',(map { \"<$_>\" } @recipients)).\"\\n\";\n-\t\t} else {\n-\t\t\tprint \"Sendmail: $smtp_server \".join(' ',@sendmail_parameters).\"\\n\";\n \t\t}\n+\n \t\tprint $header, \"\\n\";\n-\t\tif ($smtp) {\n-\t\t\tprint \"Result: \", $smtp->code, ' ',\n-\t\t\t\t($smtp->message =~ /\\n([^\\n]+\\n)$/s), \"\\n\";\n-\t\t} else {\n-\t\t\tprint \"Result: OK\\n\";\n-\t\t}\n \t}\n \n \treturn 1;\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111069","messageId":"1239476908-25944-10-git-send-email-mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-9-git-send-email-mfwitten@gmail.com","subject":"[PATCH RFC 10/10] send-email: --compose takes optional argument to existing file","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:08:28Z","receivedAt":"2009-04-11T19:08:28Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Now, a user may specify an existing (in-progress) file to use as\nthe introductory/summary email.\n\nThe file is opened for any additional editing as usual, but it\nis not deleted upon normal termination.\n\nThere are also a number of fixes to how the internals and\ntemporaries are handled.\n\nSigned-off-by: Michael Witten <mfwitten@gmail.com>\n---\n Documentation/git-send-email.txt |   39 ++++++--\n git-send-email.perl              |  190 ++++++++++++++++++++++++--------------\n 2 files changed, 151 insertions(+), 78 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 07c831e..a2af3e5 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -60,17 +60,38 @@ The --bcc option must be repeated for each user you want on the bcc list.\n +\n The --cc option must be repeated for each user you want on the cc list.\n \n---compose::\n-\tUse $GIT_EDITOR, core.editor, $VISUAL, or $EDITOR to edit an\n-\tintroductory message for the patch series.\n+--compose[=<path>]::\n+\tUse `$GIT_EDITOR`, 'core.editor', `$VISUAL`, or `$EDITOR`, or\n+\t`vi` to edit an introductory message for the patch series. A\n+\tpath for the intermediate composition may be given. If the path\n+\tdoesn't exist, a file with default contents is created at the\n+\tpath and opened for editing. If the path does exist, then the\n+\tfile at that path is opened for editing as-is. If no path is\n+\tspecified, a new temporary file is created with some default\n+\tcontents. Upon the successful completion of send-email, all\n+\ttemporary files are automatically unlinked (deleted). However,\n+\tif send-email is terminated by a trappable signal, then this\n+\ttemporary file is not unlinked, and the user is informed of its\n+\tpath.\n +\n-When '--compose' is used, git send-email will use the From, Subject, and\n-In-Reply-To headers specified in the message. If the body of the message\n-(what you type after the headers and a blank line) only contains blank\n-(or GIT: prefixed) lines the summary won't be sent, but From, Subject,\n-and In-Reply-To headers will be used unless they are removed.\n+The user actually composes what will become a valid email message;\n+therefore, the message must have the following form (as described in\n+`RFC 822`):\n +\n-Missing From or In-Reply-To headers will be prompted for.\n+\t<headers>\n+\t<blank line>\n+\t<body>\n++\n+In particular, `<headers>` must contain the \"`Subject`\" header. Once the\n+user saves the message and quits the editor, this intermediate message is\n+transformed into the final email message by removing all lines that begin\n+with \"`GIT:`\". If the `<body>` of the final version is empty, then the\n+email is not sent, and send-email proceeds as if '--compose' had never been\n+used.\n++\n+The \"`From`\", \"`Subject`\", and \"`In-Reply-To`\" headers are taken directly\n+from the message; missing \"`From`\" or \"`In-Reply-To`\" headers will be\n+prompted for.\n \n --from=<address>::\n \tSpecify the sender of the emails.  This will default to\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex e771720..877732f 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -63,10 +63,9 @@ git send-email [options] <file | directory | rev-list options >\n     --bcc               <address>  * Email Bcc:\n     --subject            <string>  * Email \"Subject:\"\n     --in-reply-to    <message-id>  * Email \"In-Reply-To:\"; include '<' and '>'.\n+    --compose             [<path>] * Open an editor for introduction.\n     --annotate                     * Review each patch that will be sent in\n                                      an editor.\n-    --compose                      * Open an editor for introduction.\n-\n   Sending:\n     --envelope-sender   <address>  * Email envelope sender.\n     --smtp-server          <host>  * Outgoing SMTP server to use.\n@@ -173,7 +172,7 @@ if ($@) {\n # Behavior modification variables\n my ($quiet, $dry_run) = (0, 0);\n my $format_patch;\n-my $compose_filename;\n+my ($compose_filename, $compose_final_filename);\n \n # Handle interactive edition of files.\n my $multiedit;\n@@ -239,16 +238,15 @@ sub signal_handler {\n \tsystem \"stty echo\";\n \n \t# tmp files from --compose\n-\tif (defined $compose_filename) {\n-\t\tif (-e $compose_filename) {\n-\t\t\tprint \"'$compose_filename' contains an intermediate version of the email you were composing.\\n\";\n-\t\t}\n-\t\tif (-e ($compose_filename . \".final\")) {\n-\t\t\tprint \"'$compose_filename.final' contains the composed email.\\n\"\n-\t\t}\n+\tif (defined $compose_filename and -f $compose_filename) {\n+\t\tprint \"'$compose_filename' contains an intermediate version of the email you were composing.\\n\";\n+\t}\n+\n+\tif (defined $compose_final_filename) {\n+\t\tunlink $compose_final_filename if defined $compose_final_filename;\n \t}\n \n-\texit;\n+\texit 1;\n };\n \n $SIG{TERM} = \\&signal_handler;\n@@ -273,8 +271,8 @@ my $rc = GetOptions(\n \t\"smtp-ssl\" => sub { $smtp_encryption = 'ssl' },\n \t\"smtp-encryption=s\" => \\$smtp_encryption,\n \t\"identity=s\" => \\$identity,\n+\t\"compose:s\" => \\$compose,\n \t\"annotate\" => \\$annotate,\n-\t\"compose\" => \\$compose,\n \t\"quiet\" => \\$quiet,\n \t\"cc-cmd=s\" => \\$cc_cmd,\n \t\"suppress-from!\" => \\$suppress_from,\n@@ -596,36 +594,69 @@ sub get_patch_subject($) {\n \tdie \"'Subject:' line expected in '$patch'\";\n }\n \n-if ($compose) {\n-\t# Note that this does not need to be secure, but we will make a small\n-\t# effort to have it be unique\n-\t$compose_filename = ($repo ?\n-\t\ttempfile(\".gitsendemail.msg.XXXXXX\", DIR => $repo->repo_path()) :\n-\t\ttempfile(\".gitsendemail.msg.XXXXXX\", DIR => \".\"))[1];\n-\topen(C,\">\",$compose_filename)\n-\t\tor die \"Failed to open for writing $compose_filename: $!\";\n-\n-\n-\tmy $tpl_sender = $sender || $repoauthor || $repocommitter || '';\n-\tmy $tpl_subject = $initial_subject || '';\n-\tmy $tpl_reply_to = $initial_reply_to || '';\n-\n-\tprint C <<EOT;\n-From $tpl_sender # This line is ignored.\n-GIT: Lines beginning in \"GIT:\" will be removed.\n-GIT: Consider including an overall diffstat or table of contents\n-GIT: for the patch you are writing.\n-GIT:\n-GIT: Clear the body content if you don't wish to send a summary.\n-From: $tpl_sender\n-Subject: $tpl_subject\n-In-Reply-To: $tpl_reply_to\n+if (defined $compose) {{\n \n-EOT\n-\tfor my $f (@files) {\n-\t\tprint C \"GIT: \", get_patch_subject($f), \"\\n\";\n+\t# Some parameters for creating temporary files:\n+\n+\tmy $template = \".gitsendemail.msg.XXXXXX\";\n+\tmy @dir = (DIR => ($repo ? $repo->repo_path() : \".\"));\n+\tmy @suffix = (SUFFIX => \".final\");\n+\n+\t# Figure out the file that the user should be editing:\n+\n+\tmy $compose_file;\n+\tmy $needs_default_contents;\n+\n+\tif ($compose eq '') { # if no path was given\n+\t\t$needs_default_contents = 1;\n+\t\t($compose_file, $compose_filename) = tempfile($template, @dir)\n+\t\t\tor die \"--compose: Could not create temporary file for the user to edit: $!\\n\";\n+\t} else {\n+\t\t$compose_filename = $compose;\n+\t\t$needs_default_contents = not -f $compose_filename;\n \t}\n-\tclose(C);\n+\n+\t# Fill in default contents if necessary:\n+\n+\tif ($needs_default_contents) {\n+\n+\t\topen $compose_file, \">\", $compose_filename;\n+\n+\t\t# For convenience:\n+\n+\t\tlocal *STDOUT = $compose_file;\n+\n+\t\t# Help the user out with some instruction and initial headers:\n+\n+\t\tmy $from = $sender || $repoauthor || $repocommitter || '';\n+\t\tmy $subject = $initial_subject || '';\n+\t\tmy $reply_to = $initial_reply_to || '';\n+\n+\t\tprint \"From $from # This line is ignored.\\n\";\n+\t\tprint \"GIT:\\n\";\n+\t\tprint \"GIT: Lines beginning in 'GIT:' will be removed.\\n\";\n+\t\tprint \"GIT:\\n\";\n+\t\tprint \"GIT: Consider including an overall diffstat\\n\";\n+\t\tprint \"GIT: (git diff --stat) or table of contents\\n\";\n+\t\tprint \"GIT: (as provide below).\\n\";\n+\t\tprint \"GIT:\\n\";\n+\t\tprint \"GIT: Clear the body content if you decide not\\n\";\n+\t\tprint \"GIT: to send this message.\\n\";\n+\t\tprint \"GIT:\\n\";\n+\t\tprint \"GIT: Here are the <headers>:\\n\";\n+\t\tprint \"From: $from\\n\";\n+\t\tprint \"Subject: $subject\\n\";\n+\t\tprint \"In-Reply-To: $reply_to\\n\";\n+\t\tprint \"\\n\";\n+\t\tprint \"GIT: This is the first line of the <body>:\\n\";\n+\t\tprint \"\\n\";\n+\n+\t\tfor my $f (@files) {\n+\t\t\tprint \"GIT: \", get_patch_subject($f), \"\\n\";\n+\t\t}\n+\t}\n+\n+\t# Do the editing:\n \n \tmy $editor = $ENV{GIT_EDITOR} || Git::config(@repo, \"core.editor\") || $ENV{VISUAL} || $ENV{EDITOR} || \"vi\";\n \n@@ -635,23 +666,40 @@ EOT\n \t\tdo_edit($compose_filename);\n \t}\n \n-\topen(C2,\">\",$compose_filename . \".final\")\n-\t\tor die \"Failed to open $compose_filename.final : \" . $!;\n+\t# Now transform the user-edited introduction into something\n+\t# suitable for sending via email; the user's editor may have\n+\t# unlinked the original file and replaced it with an entirely\n+\t# new one. If this be the case, then it wouldn't do just to seek\n+\t# to the beginning and start reading, because then only the\n+\t# original content would be retrieved. Consequently, the file\n+\t# must be reopened to be safe (note, the original filehandle is\n+\t# closed automatically):\n+\n+\tunless (-f $compose_filename) {\n+\t\tprint \"--compose: File '$compose_filename' doesn't exist; not sending.\\n\";\n+\t\tlast;\n+\t}\n+\n+\topen $compose_file, \"<\", $compose_filename\n+\t\tor die \"--compose: Failed to open '$compose_filename' for reading: $!\";\n \n-\topen(C,\"<\",$compose_filename)\n-\t\tor die \"Failed to open $compose_filename : \" . $!;\n+\t# Create the final version:\n \n+\t(my $compose_final_file, $compose_final_filename) = tempfile($template, @dir, @suffix)\n+\t\tor die \"--compose: Could not create temporary file for final version: $!\\n\";\n+\n+\tmy ($subject, $reply_to, $from);\n \tmy $need_8bit_cte = file_has_nonascii($compose_filename);\n \tmy $in_body = 0;\n \tmy $summary_empty = 1;\n-\twhile(<C>) {\n+\twhile(<$compose_file>) {\n \t\tnext if m/^GIT:/;\n \t\tif ($in_body) {\n \t\t\t$summary_empty = 0 unless (/^\\n$/);\n \t\t} elsif (/^\\n$/) {\n \t\t\t$in_body = 1;\n \t\t\tif ($need_8bit_cte) {\n-\t\t\t\tprint C2\n+\t\t\t\tprint $compose_final_file\n \t\t\t\t\t\"MIME-Version: 1.0\\n\",\n \t\t\t\t\t\"Content-Type: text/plain; \",\n \t\t\t\t\t\"charset=utf-8\\n\",\n@@ -660,33 +708,31 @@ EOT\n \t\t} elsif (/^MIME-Version:/i) {\n \t\t\t$need_8bit_cte = 0;\n \t\t} elsif (/^Subject:\\s*(.+)\\s*$/i) {\n-\t\t\t$initial_subject = $1;\n-\t\t\tmy $subject = $initial_subject;\n-\t\t\t$_ = \"Subject: \" .\n-\t\t\t\t($subject =~ /[^[:ascii:]]/ ?\n-\t\t\t\tquote_rfc2047($subject) :\n-\t\t\t\t$subject) .\n-\t\t\t\t\"\\n\";\n+\t\t\t$subject = $1;\n+\t\t\tnext;\n \t\t} elsif (/^In-Reply-To:\\s*(.+)\\s*$/i) {\n-\t\t\t$initial_reply_to = $1;\n+\t\t\t$reply_to = $1;\n \t\t\tnext;\n \t\t} elsif (/^From:\\s*(.+)\\s*$/i) {\n-\t\t\t$sender = $1;\n+\t\t\t$from = $1;\n \t\t\tnext;\n \t\t} elsif (/^(?:To|Cc|Bcc):/i) {\n \t\t\tprint \"To/Cc/Bcc fields are not interpreted yet, they have been ignored\\n\";\n \t\t\tnext;\n \t\t}\n-\t\tprint C2 $_;\n-\t}\n-\tclose(C);\n-\tclose(C2);\n \n-\tif ($summary_empty) {\n-\t\tprint \"Summary email is empty, skipping it\\n\";\n-\t\t$compose = -1;\n+\t\tprint $compose_final_file $_;\n \t}\n-} elsif ($annotate) {\n+\n+\tprint(\"Summary email is empty, skipping it.\\n\"), last if ($summary_empty);\n+\n+\t$initial_subject = $subject;\n+\t$initial_reply_to = $reply_to;\n+\t$sender = $from;\n+\n+\tunshift(@files, $compose_final_filename);\n+\n+}} elsif ($annotate) {\n \tdo_edit(@files);\n }\n \n@@ -776,10 +822,6 @@ if (defined $smtp_server and $smtp_server ne '') {\n \t$smtp_server ||= '127.0.0.1';\n }\n \n-if ($compose && $compose > 0) {\n-\t@files = ($compose_filename . \".final\", @files);\n-}\n-\n # Variables we set as part of the loop over files\n our ($message_id, %mail, $subject, $reply_to, $references, $message,\n \t$needs_confirm, $message_num, $ask_default);\n@@ -924,9 +966,12 @@ sub send_message\n \tmy $sanitized_sender = sanitize_address($sender);\n \tmake_message_id() unless defined($message_id);\n \n+\tmy $has_non_ascii = ($subject =~ /[^[:ascii:]]/);\n+\tmy $sanitized_subject = $has_non_ascii ? quote_rfc2047($subject) : $subject;\n+\n \tmy $header = \"From: $sanitized_sender\n To: $to${ccline}\n-Subject: $subject\n+Subject: $sanitized_subject\n Date: $date\n Message-Id: $message_id\n X-Mailer: git-send-email $gitversion\n@@ -1286,7 +1331,14 @@ for (my $index = 0; $index < @files; $index++) {\n cleanup_compose_files();\n \n sub cleanup_compose_files() {\n-\tunlink($compose_filename, $compose_filename . \".final\") if $compose;\n+\n+\tif (defined $compose_final_filename) {\n+\t\tunlink $compose_final_filename;\n+\t}\n+\n+\tif (defined $compose_filename and not $compose) {\n+\t\tunlink $compose_filename;\n+\t}\n }\n \n $smtp->quit if $smtp;\n-- \n1.6.2.2.479.g2aec\n"},{"id":"111068","messageId":"fabb9a1e0904111217t55fc0fd1y8d2b8b3a156e4f21@mail.gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-7-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 07/10] send-email: Remove horrible mix of tabs and spaces","fromName":"Sverre Rabbelier","fromEmail":"srabbelier@gmail.com","sentAt":"2009-04-11T19:17:30Z","receivedAt":"2009-04-11T19:17:30Z","isPatch":true,"sender":{"key":"srabbelier@gmail.com","avatar":"https://avatars.githubusercontent.com/u/3098?v=4"},"body":"Heya,\n\nOn Sat, Apr 11, 2009 at 21:08, Michael Witten <mfwitten@gmail.com> wrote:\n> +## WARNING! ACHTUNG! ATTENTION! ADVERTENCIA!\n> +##   Currently, this file uses tabs (like the rest of git source) to\n> +##   delineate code structure. Do NOT under any circumstances mix tabs\n> +##   and spaces across lines that share a relationship in terms of layout.\n> +##   In fact, it would currently be best to use only tabs, so please set\n> +##   your editor(s) accordingly. This code is already trashy enough. Please\n> +##   don't make it worse.\n\nIsn't this a bit overkill? In fact, isn't it overkill a lot?\n\n-- \nCheers,\n\nSverre Rabbelier\n"},{"id":"111081","messageId":"fabb9a1e0904111225x7a8915a4q78202f397f9dc971@mail.gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-10-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 10/10] send-email: --compose takes optional argument to existing file","fromName":"Sverre Rabbelier","fromEmail":"srabbelier@gmail.com","sentAt":"2009-04-11T19:25:20Z","receivedAt":"2009-04-11T19:25:20Z","isPatch":true,"sender":{"key":"srabbelier@gmail.com","avatar":"https://avatars.githubusercontent.com/u/3098?v=4"},"body":"Heya,\n\nOn Sat, Apr 11, 2009 at 21:08, Michael Witten <mfwitten@gmail.com> wrote:\n> Now, a user may specify an existing (in-progress) file to use as\n> +with \"`GIT:`\". If the `<body>` of the final version is empty, then the\n> +email is not sent, and send-email proceeds as if '--compose' had never been\n> +used.\n\nOuch! Wouldn't it be better to abort instead? Allover git we abort on\nempty commit messages and the like, why not here?\n\n-- \nCheers,\n\nSverre Rabbelier\n"},{"id":"111084","messageId":"b4087cc50904111231j1585421bw35942d7ca630a41@mail.gmail.com","threadId":"18833","inReplyTo":"fabb9a1e0904111217t55fc0fd1y8d2b8b3a156e4f21@mail.gmail.com","subject":"Re: [PATCH RFC 07/10] send-email: Remove horrible mix of tabs and spaces","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:31:47Z","receivedAt":"2009-04-11T19:31:47Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"On Sat, Apr 11, 2009 at 14:17, Sverre Rabbelier <srabbelier@gmail.com> wrote:\n> Isn't this a bit overkill? In fact, isn't it overkill a lot?\n\n;-D\n\nIn my experience... NO.\n"},{"id":"111085","messageId":"b4087cc50904111238s4f1fc8a7v79ba06eb6fb48cb@mail.gmail.com","threadId":"18833","inReplyTo":"fabb9a1e0904111225x7a8915a4q78202f397f9dc971@mail.gmail.com","subject":"Re: [PATCH RFC 10/10] send-email: --compose takes optional argument to existing file","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T19:38:06Z","receivedAt":"2009-04-11T19:38:06Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"On Sat, Apr 11, 2009 at 14:25, Sverre Rabbelier <srabbelier@gmail.com> wrote:\n> Ouch! Wouldn't it be better to abort instead? Allover git we abort on\n> empty commit messages and the like, why not here?\n\nI was just following the original behavior. I don't really mind either way.\n"},{"id":"111102","messageId":"loom.20090411T213511-518@post.gmane.org","threadId":"18833","inReplyTo":"1239476908-25944-2-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 02/10] Docs: send-email: Remove superfluous information in CONFIGURATION","fromName":"Stephen Boyd","fromEmail":"bebarino@gmail.com","sentAt":"2009-04-11T21:42:13Z","receivedAt":"2009-04-11T21:42:13Z","isPatch":true,"sender":{"key":"bebarino@gmail.com","avatar":"https://avatars.githubusercontent.com/u/38832?v=4"},"body":"Michael Witten <mfwitten <at> gmail.com> writes:\n> \n> There is now a comment block warning trespassers.\n\nThis patch and the previous have these comment block warnings which look ugly to\nme. Maybe we should make a DocumentationGuidelines, in the same spirit as\nCodingGuidelines where we can place these policies.\n\nAlso, the alphabetical ordering of patch 1 is nice, but if we want to do this we\nshould probably change every git-<command>.txt to be consistent.\n"},{"id":"111104","messageId":"loom.20090411T214618-958@post.gmane.org","threadId":"18833","inReplyTo":"1239476908-25944-6-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 06/10] send-email: References: should only reference what is actually sent","fromName":"Stephen Boyd","fromEmail":"bebarino@gmail.com","sentAt":"2009-04-11T21:52:21Z","receivedAt":"2009-04-11T21:52:21Z","isPatch":true,"sender":{"key":"bebarino@gmail.com","avatar":"https://avatars.githubusercontent.com/u/38832?v=4"},"body":"Michael Witten <mfwitten <at> gmail.com> writes:\n\n> \n> +# returns 1 of the message was sent, 0 otherwise.\n\ns/of/if/\n"},{"id":"111105","messageId":"loom.20090411T215335-597@post.gmane.org","threadId":"18833","inReplyTo":"1239476908-25944-9-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 09/10] send-email: Minor cleanup of $smtp_server usage and send_message()","fromName":"Stephen Boyd","fromEmail":"bebarino@gmail.com","sentAt":"2009-04-11T21:58:14Z","receivedAt":"2009-04-11T21:58:14Z","isPatch":true,"sender":{"key":"bebarino@gmail.com","avatar":"https://avatars.githubusercontent.com/u/38832?v=4"},"body":"Michael Witten <mfwitten <at> gmail.com> writes:\n\n> \n>  \tbe specified by the 'sendemail.smtpserver' configuration\n>  \toption; the built-in default is `/usr/sbin/sendmail` or\n>  \t`/usr/lib/sendmail` if such program is available, or\n> -\t`localhost` otherwise.\n> +\t`127.0.0.1` otherwise. Also, if <host> is the empty string,\n> +\tthen a built-in default is used.\n\nDoes this help anyone? localhost at least doesn't change when/if ipv6 is used,\nwhereas '127.0.0.1' is only for ipv4.\n"},{"id":"111106","messageId":"b4087cc50904111513j784d52aao26ae9a5569c8c7de@mail.gmail.com","threadId":"18833","inReplyTo":"loom.20090411T215335-597@post.gmane.org","subject":"Re: [PATCH RFC 09/10] send-email: Minor cleanup of $smtp_server usage and send_message()","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T22:13:56Z","receivedAt":"2009-04-11T22:13:56Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"On Sat, Apr 11, 2009 at 16:58, Stephen Boyd <bebarino@gmail.com> wrote:\n> Michael Witten <mfwitten <at> gmail.com> writes:\n>\n>>\n>>       be specified by the 'sendemail.smtpserver' configuration\n>>       option; the built-in default is `/usr/sbin/sendmail` or\n>>       `/usr/lib/sendmail` if such program is available, or\n>> -     `localhost` otherwise.\n>> +     `127.0.0.1` otherwise. Also, if <host> is the empty string,\n>> +     then a built-in default is used.\n>\n> Does this help anyone? localhost at least doesn't change when/if ipv6 is used,\n> whereas '127.0.0.1' is only for ipv4.\n\nAh. Good point. I'll get rid of that change.\n"},{"id":"111107","messageId":"b4087cc50904111542v37898b53we755ab044621ddab@mail.gmail.com","threadId":"18833","inReplyTo":"loom.20090411T214618-958@post.gmane.org","subject":"Re: [PATCH RFC 06/10] send-email: References: should only reference what is actually sent","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-11T22:42:55Z","receivedAt":"2009-04-11T22:42:55Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"On Sat, Apr 11, 2009 at 16:52, Stephen Boyd <bebarino@gmail.com> wrote:\n> Michael Witten <mfwitten <at> gmail.com> writes:\n>\n>>\n>> +# returns 1 of the message was sent, 0 otherwise.\n>\n> s/of/if/\n\nWoops! Thanks!\n"},{"id":"111112","messageId":"76718490904111927y683ee4axe512dae9d58e19bb@mail.gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-8-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 08/10] send-email: Add --sleep for email throttling","fromName":"Jay Soffian","fromEmail":"jaysoffian@gmail.com","sentAt":"2009-04-12T02:27:29Z","receivedAt":"2009-04-12T02:27:29Z","isPatch":true,"sender":{"key":"jaysoffian@gmail.com","avatar":"https://avatars.githubusercontent.com/u/155970?v=4"},"body":"On Sat, Apr 11, 2009 at 3:08 PM, Michael Witten <mfwitten@gmail.com> wrote:\n> +if (defined $sleep) {{\n> +}}\n\nWhat's the double-brackets about?\n\nj.\n"},{"id":"111114","messageId":"f661ba4e-cfb0-4756-8ef4-4a4f9f66c4e8mfwitten@gmail.com","threadId":"18833","inReplyTo":"1239476908-25944-8-git-send-email-mfwitten@gmail.com","subject":"Re: [PATCH RFC 08/10] send-email: Add --sleep for email throttling","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-12T02:59:57Z","receivedAt":"2009-04-12T02:59:57Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"On Sat, Apr 11, 2009 at 21:27, Jay Soffian <jaysoffian@gmail.com> wrote:\n> On Sat, Apr 11, 2009 at 3:08 PM, Michael Witten <mfwitten@gmail.com> wrote:\n>> +if (defined $sleep) {{\n>> +}}\n>\n> What's the double-brackets about?\n\nThe {} that form the true-body of the if statement don't actually\ndenote a block. The extra layer of {} is explicitly creating a block.\nThis is done, because in Perl, blocks can be thought of as loops that\nexecute one iteration, so you can use all of the loop flow-control\noperators 'redo', 'last', and 'next'.\n\nIn this case, I wanted to use 'last' to jump out of --sleep setup\nshould the user decide to do so, because I think it's cleaner than a\ngoto or variable check or superfluous loop:\n\nif (defined $sleep) {{\n\n\tunless ($chain_reply_to) {\n\t\t...\n\t\t/^b/                                               or\n\t\t/^s/ and $chain_reply_to = 1                       or\n\t\t/^c/ and $sleep = undef, last                      or  # forget --sleep was ever used\n\t\t/^n/ and $chain_reply_to = 1, $sleep = undef, last or  # forget --sleep was ever used\n\t\t/^q/ and exit;\n\t}\n\t...\n}}\n# last jumps to here\n\nAnyway, this particular behavior was requested (and seems reasonable):\n\n\thttp://marc.info/?l=git&m=123929919621279&w=2\n\nSincerely,\nMichael Witten\n"},{"id":"111147","messageId":"buoljq5cogy.fsf@dhlpc061.dev.necel.com","threadId":"18833","inReplyTo":"fabb9a1e0904111217t55fc0fd1y8d2b8b3a156e4f21@mail.gmail.com","subject":"Re: [PATCH RFC 07/10] send-email: Remove horrible mix of tabs and spaces","fromName":"Miles Bader","fromEmail":"miles@gnu.org","sentAt":"2009-04-13T01:49:17Z","receivedAt":"2009-04-13T01:49:17Z","isPatch":true,"sender":{"key":"miles@gnu.org","avatar":"https://gravatar.com/avatar/01069b69593af7bff28e2f97afeb3644ae6fe2f5f56cb3a8cf34c5fb8c36efe5?d=mp&s=160"},"body":"Sverre Rabbelier <srabbelier@gmail.com> writes:\n>> +## WARNING! ACHTUNG! ATTENTION! ADVERTENCIA!\n>> +##   Currently, this file uses tabs (like the rest of git source) to\n>> +##   delineate code structure. Do NOT under any circumstances mix tabs\n>> +##   and spaces across lines that share a relationship in terms of layout.\n>> +##   In fact, it would currently be best to use only tabs, so please set\n>> +##   your editor(s) accordingly. This code is already trashy enough. Please\n>> +##   don't make it worse.\n>\n> Isn't this a bit overkill? In fact, isn't it overkill a lot?\n\n\"Bizarre\" is the word I'd use...\n\n[There are places to whine about whitespace conventions, but that place\nisn't giant screaming comments in individual source files...]\n\n-miles\n\n-- \nAdmiration, n. Our polite recognition of another's resemblance to ourselves.\n"},{"id":"111148","messageId":"b4087cc50904121915u70fbf82fj34ec619b59830b1e@mail.gmail.com","threadId":"18833","inReplyTo":"buoljq5cogy.fsf@dhlpc061.dev.necel.com","subject":"Re: [PATCH RFC 07/10] send-email: Remove horrible mix of tabs and spaces","fromName":"Michael Witten","fromEmail":"mfwitten@gmail.com","sentAt":"2009-04-13T02:15:38Z","receivedAt":"2009-04-13T02:15:38Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"On Sun, Apr 12, 2009 at 20:49, Miles Bader <miles@gnu.org> wrote:\n> Sverre Rabbelier <srabbelier@gmail.com> writes:\n>>> +## WARNING! ACHTUNG! ATTENTION! ADVERTENCIA!\n>>> +##   Currently, this file uses tabs (like the rest of git source) to\n>>> +##   delineate code structure. Do NOT under any circumstances mix tabs\n>>> +##   and spaces across lines that share a relationship in terms of layout.\n>>> +##   In fact, it would currently be best to use only tabs, so please set\n>>> +##   your editor(s) accordingly. This code is already trashy enough. Please\n>>> +##   don't make it worse.\n>>\n>> Isn't this a bit overkill? In fact, isn't it overkill a lot?\n>\n> \"Bizarre\" is the word I'd use...\n\nWhatever you say, Master Bader.\n"}]}