Wysłać wiadomość e-mail do wielu odbiorców za pomocą wiadomości MailMessage?


85

Mam wielu odbiorców wiadomości e-mail przechowywanych w programie SQL Server. Kiedy kliknę wyślij na stronie internetowej, powinna wysłać e-mail do wszystkich odbiorców. Oddzieliłem e-maile za pomocą ;.

Poniżej znajduje się kod pojedynczego odbiorcy.

MailMessage Msg = new MailMessage();
MailAddress fromMail = new MailAddress(fromEmail);
Msg.From = fromMail;
Msg.To.Add(new MailAddress(toEmail));

if (ccEmail != "" && bccEmail != "")
{
    Msg.CC.Add(new MailAddress(ccEmail));
    Msg.Bcc.Add(new MailAddress(bccEmail));
}

SmtpClient a = new SmtpClient("smtp server name");
a.Send(Msg);
sreader.Dispose();

Czego próbowałeś do tej pory? Czy to działa dla jednego odbiorcy?
Brendan Green

@BrendanGreen tak, pracuję dla jednego odbiorcy.
Chetan Goenka

5
Poza tym do Twojej wiadomości, Twoje MailMessagei SmtpClientinstancje muszą znajdować się w usingblokach.
John Saunders

2
@JohnSaunders Powinni, ale na pewno nie muszą .
Num Lock

1
@JohnSaunders Po pierwsze, twoje sformułowanie jest bardzo mylące: prawdopodobnie będziesz się o to spierać, ale „musi być w usingblokach” nie równa się „musi zostać usunięty”. Po drugie, w kodzie produkcyjnym, takim jak aplikacje internetowe, zazwyczaj i SendAsynctak będziesz chciał użyć , co działa zgodnie z przeznaczeniem, bez konieczności usuwania SnmpClientinstancji.
Num Lock

Odpowiedzi:


178

Łatwy!

Po prostu podziel listę adresów przychodzących na „;” znak i dodaj je do wiadomości e-mail:

foreach (var address in addresses.Split(new [] {";"}, StringSplitOptions.RemoveEmptyEntries))
{
    mailMessage.To.Add(address);    
}

W tym przykładzie addresseszawiera „ address1@example.com;address2@example.com”.


56
Spóźniłem się na imprezę, ale konstruktor MailMessage (ciąg od, ciąg do) akceptuje listę adresów oddzielonych przecinkami. Więc mogłeś zrobić coś takiego jak nowa MailMessage (fromMail, address.replace (";", ",")) Może nie lepiej jest użyć zamiany, ale czuję, że powinienem to skomentować na wypadek, gdyby inni ludzie już rozdzielili przecinki smyczki! Wtedy nie byłoby potrzeby dzielenia ani wymiany.
Areks

@Areks, jeśli możesz ułożyć wiersz przykładowego kodu podobny do Brendana, zdecydowanie powinieneś dodać to jako odpowiedź.
Adam Miller

@ Areks dzięki za ten komentarz, już dzieliłem adresy, dopóki nie przeczytałem twojego komentarza. to jest dokładnie to, czego chcę!
Djeroen

Czy to konieczne? Czy nie bierzesz po prostu ciągu już sformatowanego dla wielu adresów i dzielisz je, a następnie ponownie przypisujesz? Jeśli wysyłasz Do () ciąg, jak wspomniano Do („a1; a2; a3”), dlaczego musisz je podzielić, a następnie przypisać indywidualnie? Ponieważ z wyjątkiem wielu adresów w AddressCollection lub ciągu separatora.
Casey

82

Zgodnie z sugestią Adama Millera w komentarzach dodam jeszcze jedno rozwiązanie.

Konstruktor MailMessage (String from, String to) akceptuje listę adresów oddzielonych przecinkami. Jeśli więc masz już listę oddzieloną przecinkami („,”), użycie jest tak proste, jak:

MailMessage Msg = new MailMessage(fromMail, addresses);

W tym konkretnym przypadku możemy zastąpić ';' dla ',' i nadal używaj konstruktora.

MailMessage Msg = new MailMessage(fromMail, addresses.replace(";", ","));

Niezależnie od tego, czy wolisz tę, czy zaakceptowaną odpowiedź, zależy od Ciebie. Prawdopodobnie pętla sprawia, że ​​intencja jest wyraźniejsza, ale to jest krótsze i nie niejasne. Ale jeśli masz już listę oddzieloną przecinkami, myślę, że jest to właściwy sposób.


2
Ponieważ spowodowało to problem z aplikacją, którą zarządzam, która to zaimplementowała, powinieneś sprawdzić, czy końcowym znakiem jest średnik i usunąć go przed uruchomieniem polecenia replace. Nie jestem pewien, czy kończący średnik jest uważany za prawidłową listę adresatów, ale ludzie mogą być przyzwyczajeni do wyświetlania końcowego średnika w aplikacjach takich jak Outlook. Nie możesz mieć końcowego przecinka na liście oddzielonej przecinkami, którą przekazujesz do MailMessage.
David Jacobsen

1
W moim rozumieniu nie powinno być końcowego przecinka / średnika, jeśli po tym nic nie ma ... Ale zdecydowanie dobry komentarz, aby ludzie, którzy to czytają, byli tego świadomi. Dziękuję Ci!
Areks

1
Czy jest to gdzieś udokumentowane? Dokumentacja konstruktora po prostu opisuje toparametr jako „Ciąg zawierający adres odbiorcy wiadomości e-mail”. Chcę go używać, ale nie chcę, aby jego wspornik został usunięty.
xr280xr

1
Niestety wygląda na to, że format nie został udokumentowany, ale konstruktor stwierdza, że ​​może być przeznaczony dla więcej niż jednego odbiorcy: msdn.microsoft.com/en-us/library/14k9fb7t(v=vs.110).aspx Ciąg zawierający adresy odbiorców wiadomości e-mail. Zarówno „adresy”, jak i „adresaci” są w liczbie mnogiej.
Areks

1
Zdecydowanie funkcja, ale dokumentacja jest albo rzadka, albo nie istnieje. Musiałem przejść przez około 5 wywołań metod, aby uzyskać pierwszą wskazówkę, że to prawda. referenceource.microsoft.com/#System/net/System/Net/mail/…
Sinjai

1

Zgodnie z dokumentacją:

Właściwość MailMessage.To - zwraca MailAddressCollection zawierającą listę adresatów tej wiadomości e-mail

Tutaj MailAddressCollection ma wbudowaną metodę o nazwie

   public void Add(string addresses)

   1. Summary:
          Add a list of email addresses to the collection.

   2. Parameters:
          addresses: 
                *The email addresses to add to the System.Net.Mail.MailAddressCollection. Multiple
                *email addresses must be separated with a comma character (",").     

Dlatego wymóg w przypadku wielu odbiorców: podaj ciąg zawierający adresy e-mail oddzielone przecinkami

W Twoim przypadku :

po prostu wymień wszystkie; z ,

Msg.To.Add(toEmail.replace(";", ","));

Na przykład :

  1. https://docs.microsoft.com/en-us/dotnet/api/system.net.mail.mailmessage?view=netframework-4.8
  2. https://www.geeksforgeeks.org/c-sharp-replace-method/

-4

Przetestowałem to za pomocą następującego skryptu PowerShell i używając (,) między adresami. U mnie zadziałało!

$EmailFrom = "<from@any.com>";
$EmailPassword = "<password>";
$EmailTo = "<to1@any.com>,<to2@any.com>";
$SMTPServer = "<smtp.server.com>";
$SMTPPort = <port>;
$SMTPClient = New-Object Net.Mail.SmtpClient($SmtpServer,$SMTPPort);
$SMTPClient.EnableSsl = $true;
$SMTPClient.Credentials = New-Object System.Net.NetworkCredential($EmailFrom, $EmailPassword);
$Subject = "Notification from XYZ";
$Body = "this is a notification from XYZ Notifications..";
$SMTPClient.Send($EmailFrom, $EmailTo, $Subject, $Body);

4
To jest pytanie oznaczone tagiem C#, które w ogóle nie jest związane z PowerShell
Jérôme MEVEL

Na końcu ta sama biblioteka. Jest to po prostu łatwiejsze do przetestowania przy użyciu programu PowerShell na maszynie bez lub. Po uruchomieniu skryptu PowerSell jest to tylko kwestia „przetłumaczenia” na jego odpowiednik w języku C #.
Heitor Marcos

1
To pytanie nie jest nawet oznaczone, .NET Frameworkale tylko C#. Gdyby wszyscy robili to samo, mielibyśmy również odpowiedzi w VB.NET, F # lub nawet C ++ na wszystkie pytania związane z .NET Framework. W końcu to ten sam Framework, to tylko kwestia tłumaczenia ... Widzisz, o co mi chodzi? StackOverflow stałby się naprawdę
śmieciowym
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.