Wyświetlenie prędkości wysyłania emaila z załącznikiem

0

Za pomocą System.Net.Mail i klasy SmtpClient wysyłam w programie emaile z załącznikami. Chciałbym, żeby dla każdego wysyłanego załącznika była pokazywana jego aktualna prędkość wysyłania. Jak można coś takiego zrobić?

0
int SendMailAndGetSpeed(SmtpClient client, MailMessage mail)
{
	long totalSize = (double)mail.Attachments.CastOf<Attachment>().Sum(x => x.ContentStream.Length) * (4D/3D); // base64
	Stopwatch stopWatch = new Stopwatch();
        stopWatch.Start();
        client.SendMessage(mail);
        stopWatch.Stop();

	return totalSize / stopWatch.Elapsed.TotalSeconds; // bytes per seconds

To da Ci jedynie orientacyjne wyniki.
PS. Pisane z palca.

2

SmtpClient nie ma możliwości pokazania postępu w żaden sposób. Poza tym załączniki nie są wysyłane osobno ale jako całość z treścią

0

No dobra, z SmtpClient nie da się tego zrobić. Ale musi być jakiś inny sposób, który pokazuje prędkość wysyłania w czasie rzeczywistym. Może ilość wysłanych danych podzielić przez czas, od kiedy zostały one wysłane i ciągle to odświeżać? Tylko jak zdobyć tą ilość wysłanych danych w programie (żeby nie pobrało mi przez przypadek danych wysyłanych w tym samym czasie np. w przeglądarce internetowej)?

Co znaczy:

Poza tym załączniki nie są wysyłane osobno ale jako całość z treścią
To nie działa w ten sposób, że najpierw zostaje wysyłany załącznik na serwer i dopiero gdy jest już tam cały, wiadomość z treścią i tym załącznikiem zostaje wysłana? Swoją drogą na treści mi nie zależy.

0
  1. SmtpClient nie pokazuje ile już wysłał.
  2. to znaczy, że załącznik koduje się do base64, nazywa i dodaje do treści wiadomości (to tak bardzo skrótowo)
  3. pewnie, że się da. Zapewne nawet ktoś to już zrobił i jak poszukasz to pewnie znajdziesz.
  4. jak nie znajdziesz to protokół SMTP jest dość prosty i zrobienie jego obsługi na gniazdach nie jest skomplikowane
0

Przez kilka dobrych dni próbowałem pobrać tą prędkość, np. sczytywałem pakiety przesyłane przez kartę sieciową przez GetIPv4Statistics (ale wysyłane pakiety dotyczyły wszystkich programów), próbowałem odczytać pakiety wysyłane przez konkretny program przez PerformanceCounter, ale takie rozwiązanie po prostu nie działało / otrzymana prędkość była liczbą "z kosmosu". Później szukałem jak odczytywać wysyłane bajty przez porty - także zero informacji.

Następnie przeglądnąłem wszystkie zewnętrzne biblioteki do C#, które umożliwiają wysyłanie emaili przez SMTP i mają w dokumentacji chociaż wzmiankę o ilości wysyłanych danych przez program (na tej podstawie, czyli wysłanych bajtów i czasu wysyłania, policzenie prędkości nie powinno być trudne). W końcu znalazłem: MailKit.

W jednym z plików jest interfejs, który zawiera liczbę bajtów wysłanych/pobranych przez program, o który mi chodziło:
https://github.com/jstedfast/MailKit/blob/master/MailKit/ITransferProgress.cs

Napisałem do autora biblioteki emaila, czy jest możliwe pobranie tych liczby bajtów. Oto co mi odpisał (oryginał):

There's no way to get 100% accurate upload/downloads speeds in MailKit, but MailKit does have APIs that take an ITransferProgress argument, such as the send method:

http://www.mimekit.org/docs/html/Overload_MailKit_MailTransport_Send.htm

You can implement your own ITransferProgress class that tracks transfer of data such as messages which should give you a rough idea.

This will allow you to get notifications of how much data has been uploaded (or downloaded when used with the various ImapFolder and/or Pop3Client methods), and, based on that + overall time spent, you can calculate transfer speeds.

Mam teraz pytanie, jak dostać się do tej ilości wysyłanych bajtów? Bardzo mi na tym zależy.

1

nie czytasz co się do Ciebie pisze to i szukasz czegoś, czego nie możesz znaleźć.

Wysyłanie maila przez zwykłe gniazdo (pisałem, że SMTP jest banalny) masz np. tu https://codesnipets.wordpress.com/2010/04/21/smtp-email-using-sockets-system-web-mail/
czy tu http://www.codeproject.com/Articles/7189/Socket-Console-for-SMTP-in-C

Cały myk polega na tym aby samo wysyłanie wiadomości (w pierwszym przypadku jest to linijka 167 - Senddata(s, Header.ToString());) zmienić tak aby mierzyło prędkość. Tutaj zamiast wysyłać całość Header.ToString() - należy to najpierw zapisać do bufora a następnie wysyłać partiami po np. 1kB, mierząc jednocześnie czas jaki zajmie wysyłanie tego 1kB. Następnie mając wielkość wiadomości oraz czas jaki zajęło jej wysłanie możesz policzyć średnią prędkość wysyłki.

0

Tu http://www.codeproject.com/Articles/19546/MailMergeLib-A-NET-Mail-Client-Library jest biblioteka do wysyłania maili, która umożliwia pokazanie paska postępu a więc na 100% da się zaimplementować obliczanie prędkości wysyłania.

1 użytkowników online, w tym zalogowanych: 0, gości: 1