git/list[1] front-page[2] threads[3] people[4] search[5] about
 

[PATCH v5 0/2] send-email: integrate with git imap-send

From
Aditya Garg <gargaditya08@live.com>
Date
Aug 12, 2025, 06:44 UTC
Message-ID
<PN3PR01MB9597E8E33868386C997D2563B82BA@PN3PR01MB9597.INDPRD01.PROD.OUTLOOK.COM>
In-Reply-To
<08528f201acc1038ebc5861321395d17516094fd.1753003385.git.gargaditya08@live.com>
Hi all
This patch series introduces integration of `git send-email` with `git imap-send`.

The first patch adds the ability to send a copy of sent emails to an IMAP folder specified by the user, which is useful for email providers that do not support sending a copy of sent emails to the "Sent" folder via SMTP.

The second patch allows users to copy emails to an IMAP folder without actually sending them.

v2 - Fix indentation in patch for imap-send.c
   - Minor edits to commit message
v3 - Rename imap folder to imap sent folder
   - Make an error message shorter by removing unecessary details
v4 - Fix a bug causing emails to be copied to an IMAP folder even if
     --dry-run is specified.
   - Minor edits to commit messages and docs.
   - Add another patch that enables copying emails to an IMAP folder
     without actually sending them.
v5 - Avoid using -[no-]parameter.
Aditya Garg (2):
  send-email: add ability to send a copy of sent emails to an IMAP
    folder
  send-email: enable copying emails to an IMAP folder without actually
    sending them
 Documentation/config/sendemail.adoc |  2 ++
 Documentation/git-send-email.adoc   | 26 +++++++++++++++++++
 git-send-email.perl                 | 40 +++++++++++++++++++++++++++--
 imap-send.c                         | 26 +++++++++++++------
 4 files changed, 84 insertions(+), 10 deletions(-)
Range-diff against v4:
1:  2ad311502d ! 1:  27b5eb33bb send-email: enable copying emails to IMAP folder without actually sending them
    @@ Metadata
     Author: Aditya Garg <gargaditya08@live.com>
     
      ## Commit message ##
    -    send-email: enable copying emails to IMAP folder without actually sending them
    +    send-email: add ability to send a copy of sent emails to an IMAP folder
     
    -    `git imap-send` was built on the idea of copying emails to an IMAP folder
    -    like drafts, and sending them later using an email client. Currently
    -    the only way to do it is by piping output of `git format-patch` to IMAP
    -    send.
    +    Some email providers like Apple iCloud Mail do not support sending a copy
    +    of sent emails to the "Sent" folder if SMTP server is used. As a
    +    workaround, various email clients like Thunderbird which rely on SMTP,
    +    use IMAP to send a copy of sent emails to the "Sent" folder. Something
    +    similar can be done if sending emails via `git send-email`, by using
    +    the `git imap-send` command to send a copy of the sent email to an IMAP
    +    folder specified by the user.
     
    -    Add another way to do it by using `git send-email` with the
    -    `--use-imap-only` or `sendmail.useImapOnly` option. This allows users to
    -    use the advanced features of `git send-email` like tweaking Cc: list
    -    programmatically, compose the cover letter, etc. and then send the well
    -    formatted emails to an IMAP folder using `git imap-send`.
    -
    -    While at it, use `` instead of '' for --smtp-encryption ssl in help
    -    section of `git send-email`.
    +    Add this functionality to `git send-email` by introducing a new
    +    configuration variable `sendemail.imapfolder` and command line option
    +    `--imap-folder` which specifies the IMAP folder to send a copy of the
    +    sent emails to. If specified, a copy of the sent emails will be sent
    +    by piping the emails to `git imap-send` command, after all emails are
    +    sent via SMTP and the SMTP server has been closed.
     
         Signed-off-by: Aditya Garg <gargaditya08@live.com>
     
      ## Documentation/config/sendemail.adoc ##
    -@@ Documentation/config/sendemail.adoc: sendemail.smtpServerPort::
    +@@ Documentation/config/sendemail.adoc: sendemail.smtpServer::
    + sendemail.smtpServerPort::
      sendemail.smtpServerOption::
      sendemail.smtpUser::
    - sendemail.imapSentFolder::
    -+sendemail.useImapOnly::
    ++sendemail.imapSentFolder::
      sendemail.thread::
      sendemail.transferEncoding::
      sendemail.validate::
     
      ## Documentation/git-send-email.adoc ##
     @@ Documentation/git-send-email.adoc: must be used for each option.
    - This feature requires setting up `git imap-send`. See linkgit:git-imap-send[1]
    - for instructions.
    + 	commands and replies will be printed. Useful to debug TLS
    + 	connection and authentication problems.
      
    -+--[no-]use-imap-only::
    -+	If this is set, all emails will only be copied to the IMAP folder specified
    -+	with `--imap-sent-folder` or `sendemail.imapSentFolder` and will not be sent
    -+	to the recipients. Useful if you just want to create a draft of the emails
    -+	and use another email client to send them.
    -+	If disabled with `--no-use-imap-only`, the emails will be sent like usual.
    -+	Disabled by default, but the `sendemail.useImapOnly` configuration
    -+	variable can be used to enable it.
    -+
    ++--imap-sent-folder=<folder>::
    ++	Some email providers (e.g. iCloud) do not send a copy of the emails sent
    ++	using SMTP to the `Sent` folder or similar in your mailbox. Use this option
    ++	to use `git imap-send` to send a copy of the emails to the folder specified
    ++	using this option. You can run `git imap-send --list` to get a list of
    ++	valid folder names, including the correct name of the `Sent` folder in
    ++	your mailbox. You can also use this option to send emails to a dedicated
    ++	IMAP folder of your choice.
     ++
     +This feature requires setting up `git imap-send`. See linkgit:git-imap-send[1]
     +for instructions.
    @@ Documentation/git-send-email.adoc: must be used for each option.
     
      ## git-send-email.perl ##
     @@ git-send-email.perl: sub usage {
    -     --smtp-user             <str>  * Username for SMTP-AUTH.
    -     --smtp-pass             <str>  * Password for SMTP-AUTH; not necessary.
    -     --smtp-encryption       <str>  * tls or ssl; anything else disables.
    --    --smtp-ssl                     * Deprecated. Use '--smtp-encryption ssl'.
    -+    --smtp-ssl                     * Deprecated. Use `--smtp-encryption ssl`.
    -     --smtp-ssl-cert-path    <str>  * Path to ca-certificates (either directory or file).
    -                                      Pass an empty string to disable certificate
    -                                      verification.
    -@@ git-send-email.perl: sub usage {
    +     --no-smtp-auth                 * Disable SMTP authentication. Shorthand for
    +                                      `--smtp-auth=none`
          --smtp-debug            <0|1>  * Disable, enable Net::SMTP debug.
    -     --imap-sent-folder      <str>  * IMAP folder where a copy of the emails should be sent.
    -                                      Make sure `git imap-send` is set up to use this feature.
    -+    --[no-]use-imap-only           * Only copy emails to the IMAP folder specified by
    -+                                     `--imap-sent-folder` instead of actually sending them.
    ++    --imap-sent-folder      <str>  * IMAP folder where a copy of the emails should be sent.
    ++                                     Make sure `git imap-send` is set up to use this feature.
      
          --batch-size            <int>  * send max <int> message per connection.
          --relogin-delay         <int>  * delay <int> seconds between two successive login.
    -@@ git-send-email.perl: sub do_edit {
    - my $target_xfer_encoding = 'auto';
    - my $forbid_sendmail_variables = 1;
    - my $outlook_id_fix = 'auto';
    -+my $use_imap_only = 0;
    +@@ git-send-email.perl: sub format_2822_time {
      
    - my %config_bool_settings = (
    -     "thread" => \$thread,
    + # Variables we fill in automatically, or via prompting:
    + my (@to,@cc,@xh,$envelope_sender,
    +-	$initial_in_reply_to,$reply_to,$initial_subject,@files,
    ++	$initial_in_reply_to,$reply_to,$initial_subject,@files,@imap_copy,
    + 	$author,$sender,$smtp_authpass,$annotate,$compose,$time);
    + # Things we either get from config, *or* are overridden on the
    + # command-line.
     @@ git-send-email.perl: sub do_edit {
    -     "forbidsendmailvariables" => \$forbid_sendmail_variables,
    -     "mailmap" => \$mailmap,
    -     "outlookidfix" => \$outlook_id_fix,
    -+    "useimaponly" => \$use_imap_only,
    - );
    - 
    - my %config_settings = (
    + my ($smtp_authuser, $smtp_encryption, $smtp_ssl_cert_path);
    + my ($batch_size, $relogin_delay);
    + my ($identity, $aliasfiletype, @alias_files, $smtp_domain, $smtp_auth);
    ++my ($imap_sent_folder);
    + my ($confirm);
    + my (@suppress_cc);
    + my ($auto_8bit_encoding);
    +@@ git-send-email.perl: sub do_edit {
    +     "smtpauth" => \$smtp_auth,
    +     "smtpbatchsize" => \$batch_size,
    +     "smtprelogindelay" => \$relogin_delay,
    ++    "imapsentfolder" => \$imap_sent_folder,
    +     "to" => \@config_to,
    +     "tocmd" => \$to_cmd,
    +     "cc" => \@config_cc,
     @@ git-send-email.perl: sub config_regexp {
    + 		    "smtp-domain:s" => \$smtp_domain,
      		    "smtp-auth=s" => \$smtp_auth,
      		    "no-smtp-auth" => sub {$smtp_auth = 'none'},
    - 		    "imap-sent-folder=s" => \$imap_sent_folder,
    -+		    "use-imap-only!" => \$use_imap_only,
    ++		    "imap-sent-folder=s" => \$imap_sent_folder,
      		    "annotate!" => \$annotate,
      		    "compose" => \$compose,
      		    "quiet" => \$quiet,
     @@ git-send-email.perl: sub send_message {
    + 		print "\n";
    + 	}
    + 
    ++	if ($imap_sent_folder && !$dry_run) {
    ++		my $imap_header = $header;
    ++		if (@initial_bcc) {
    ++			# Bcc is not a part of $header, so we add it here.
    ++			# This is only for the IMAP copy, not for the actual email
    ++			# sent to the recipients.
    ++			$imap_header .= "Bcc: " . join(", ", @initial_bcc) . "\n";
    ++		}
    ++		push @imap_copy, "From git-send-email\n$imap_header\n$message";
    ++	}
    ++
    + 	return 1;
    + }
    + 
    +@@ git-send-email.perl: sub cleanup_compose_files {
    + 
    + $smtp->quit if $smtp;
    + 
    ++if ($imap_sent_folder && @imap_copy && !$dry_run) {
    ++	my $imap_input = join("\n", @imap_copy);
    ++	eval {
    ++		print "\nStarting git imap-send...\n";
    ++		my ($fh, $ctx) = Git::command_input_pipe(['imap-send', '-f', $imap_sent_folder]);
    ++		print $fh $imap_input;
    ++		Git::command_close_pipe($fh, $ctx);
    ++		1;
    ++	} or do {
    ++		warn "Warning: failed to send messages to IMAP folder $imap_sent_folder: $@";
    ++	};
    ++}
    ++
    + sub apply_transfer_encoding {
    + 	my $message = shift;
    + 	my $from = shift;
    +
    + ## imap-send.c ##
    +@@ imap-send.c: static int count_messages(struct strbuf *all_msgs)
      
    - 	if ($dry_run) {
    - 		# We don't want to send the email.
    -+	} elsif ($use_imap_only) {
    -+		die __("The destination IMAP folder is not properly defined.") if !defined $imap_sent_folder;
    - 	} elsif (defined $sendmail_cmd || file_name_is_absolute($smtp_server)) {
    - 		my $pid = open my $sm, '|-';
    - 		defined $pid or die $!;
    + 	while (1) {
    + 		if (starts_with(p, "From ")) {
    +-			p = strstr(p+5, "\nFrom: ");
    +-			if (!p) break;
    +-			p = strstr(p+7, "\nDate: ");
    +-			if (!p) break;
    +-			p = strstr(p+7, "\nSubject: ");
    +-			if (!p) break;
    +-			p += 10;
    +-			count++;
    ++			if (starts_with(p, "From git-send-email")) {
    ++				p = strstr(p+5, "\nFrom: ");
    ++				if (!p) break;
    ++				p += 7;
    ++				p = strstr(p, "\nTo: ");
    ++				if (!p) break;
    ++				p += 5;
    ++				count++;
    ++			} else {
    ++				p = strstr(p+5, "\nFrom: ");
    ++				if (!p) break;
    ++				p = strstr(p+7, "\nDate: ");
    ++				if (!p) break;
    ++				p = strstr(p+7, "\nSubject: ");
    ++				if (!p) break;
    ++				p += 10;
    ++				count++;
    ++			}
    + 		}
    + 		p = strstr(p+5, "\nFrom ");
    + 		if (!p)
-:  ---------- > 2:  1d74a857df send-email: enable copying emails to an IMAP folder without actually sending them
-- 
2.50.1
Previous: Aditya GargNext: Aditya Garg
Message 29 of 33 in “send-email: add ability to send a copy of sent emails to an IMAP folder”
  1. send-email: add ability to send a copy of sent emails to an IMAP folderAditya Garg, Jul 20, 2025
  2. send-email: add ability to send a copy of sent emails to an IMAP folderAditya Garg, Jul 21, 2025
  3. Eric SunshineJul 21, 2025
  4. Aditya GargJul 23, 2025
  5. Junio C HamanoJul 21, 2025
  6. brian m. carlsonJul 22, 2025
  7. Aditya GargJul 22, 2025
  8. Aditya GargJul 22, 2025
  9. Junio C HamanoJul 22, 2025
  10. Aditya GargJul 22, 2025
  11. Aditya GargJul 22, 2025
  12. Junio C HamanoJul 22, 2025
  13. Aditya GargJul 22, 2025
  14. Aditya GargJul 22, 2025
  15. Junio C HamanoJul 22, 2025
  16. Aditya GargJul 22, 2025
  17. Junio C HamanoJul 22, 2025
  18. Aditya GargJul 22, 2025
  19. send-email: add ability to send a copy of sent emails to an IMAP folderAditya Garg, Jul 22, 2025
  20. Aditya GargJul 23, 2025
  21. 0/2 send-email: integrate with git imap-sendAditya Garg, Jul 23, 2025
  22. 1/2 send-email: add ability to send a copy of sent emails to an IMAP folderAditya Garg, Jul 23, 2025
  23. 2/2 send-email: enable copying emails to IMAP folder without actually sending themAditya Garg, Jul 23, 2025
  24. Junio C HamanoAug 11, 2025
  25. Aditya GargAug 12, 2025
  26. Aditya GargAug 12, 2025
  27. Junio C HamanoAug 12, 2025
  28. Aditya GargAug 12, 2025
  29. 0/2 send-email: integrate with git imap-sendAditya Garg, Aug 12, 2025
  30. 1/2 send-email: add ability to send a copy of sent emails to an IMAP folderAditya Garg, Aug 12, 2025
  31. 2/2 send-email: enable copying emails to an IMAP folder without actually sending themAditya Garg, Aug 12, 2025
  32. Junio C HamanoAug 12, 2025
  33. Junio C HamanoAug 15, 2025

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.