I used Artalk XMPP nuget package in my C# application. I was able to send messages from the user account userA#domain.com to the user account userB#domain.com through Ignite OpenFire server on our LAN. There were several minor issues with the messages that are not showstoppers:
If I tried to provide a subject, it was prefixed with the word "Subject: " in the client. This is not a problem but I am wondering if this is a remote client or server thing.
The message body was wrapped in square brackets as [test message body]. This is not a big problem but I would rather avoid it, to preserve the message being sent as-is, for the possible automatic processing. Is this a remote client or server thing?
If message body contained XML, then it was sent successfully but never received. Is sending XML not allowed by XMPP protocol? Or is it a server or remote client thing?
Edit:
Since I asked the above bullet, I tried to use System.Security.SecurityElement.Escape() on the message body and wrapped it in <![CDATA[]]> and it was delievered with its XML preserved. The question still stands.
All successfully delivered messages have been also copied by userB back to userA. This is all right if userA is not interactive, but if it is also a real human being, then it may be annoying. Is this a server or remote client thing, and is there any way to avoid it? I know that the remote user's client does not do it with regular chat messages sent through a Jabber client to them.
Next, I had userB#domain.com invite userA#domain.com to a chat room conference.domain.com#conference.domain.com and tried to send messages to that chat room, still from userA#domain.com. No messages have been received in the conference room, and there was no exception thrown during the sending.
ArtalkXmppClient xmpp;
xmpp = new ArtalkXmppClient("domain.com", "userA#domain.com", "secret", 5222, true);
try
{
var msg = new Message(
"conference.domain.com#conference.domain.com",
"test message body",
"conference subject", // conference allows participants to change subject
null,
MessageType.Groupchat,
CultureInfo.CurrentCulture);
if (!xmpp.Connected)
{
xmpp.Connect("myapp");
}
xmpp.SendMessage(msg);
return true;
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
The solution to the group chat part of the question was to pre-create the group on the server before trying to send to it and to use MessageType.Chat.
The last part was counter-intuitive and I would have never figured it out, if I did not forget to enable group chat in the configuration during testing. When using MessageType.GroupChat or any type other than Chat it simply did not work.
Also, subject must be null, otherwise subject will change but no messages will be delivered. Changes of subject have to be sent on their own, separate messages without bodies.
The only side effect that I am noticing is that with group chat, as opposed to person-to-person chat, the messages appear escaped. I am not sure what escapes them as opposed to person-to-person chat, but this is kind of acceptable.
Related
I'm working on a project which receive notification from GCM server.
I've got the registration ID from GCM server and i send it to my server application which save it in the database.
My device receive the message but when I try to send another one, the precedent is replaced.
I know that we've 2 types of message:
Collapsible "send to sync"
Non-Collapsible
So without changing the name of the message, how can I get two message send at different time?
UPDATE 1:
When my device is offline (for example airport mode activated), I try
to send for example 2 messages from my application server to Google
server (I read that Google stores all the messages). But when I
desactivate this mode, I receive only the last message sent.
I use different collapse_key for different message and I receive all
of them (of course when the device online).
Is anybody knows how can I fix this?
The collapse key is relevant only to messages that were sent to the GCM server but haven't reached the destination device yet (if more than one such message has the same collapse key, only one of them will be sent to the device when it becomes online).
In your question you describe a different situation - the first message is received by the device and then the second message is received by the device and replaces the original message. That has nothing to do with GCM. It has to do with the way your application handles the received messages. For example, if your application code that receives the message displays is as a notification, it's up to you to decide whether a new message will override the existing notification or create a new notification.
You need to make sure that the value of the 'collapse_key' field in each message is different
I am looking to have C# connect to an e-mail account and process undelivered mail or failures. And I would like the failed address or the original e-mail to be written to a text file.
I'm sure I could figure out how to identify failed message. Example: WHERE subject CONTAINS 'failure', 'returned', etc.
What I do not know how to do is collect the failed address from the e-mail.
I was using a program called popmonger for a client at one point, but now it is collecting the wrong e-mail addresses. It is collecting mailer-daemon#gateway03.websitewelcome.com as an example instead of the original or failed e-mail. I thought it might be easier if I wrote a C# service.
The e-mail account I am connecting to is at hostgator. Does anyone know where to start on this?
Thanks,
Jake
Since the mail client being used is called popmonger, it sounds like you will be dealing with POP3 protocol and although .Net provides a way to send email via SMTP easily, it doesn't really do the same justice when checking emails.
You will have to use a 3rd party DLL that has a POP3 client to retrieve the emails. Most importantly you will need to inspect one of the failure email notifications to see what what your application will be expecting. There should be something common in the subject, body, originator address, etc. to tip off which emails are failure notifications. Then you need to see where in the body of the email it specifies the error information you need to retrieve to write to the text file. Basically your steps should go something like this:
Check for and retrieve email messages
Add each failure email object to a collection (List<T> works just fine)
Read/parse each email to extract the information you need
Write the extracted data to a file
As long as everything goes well and you get no exceptions, delete the email from the POP server with your POP client object (that way you don't read the same failure notices every time and fill your text file with redundant data)
I've used a POP3 class from this codeproject article and it does include code for attachments but I never use it for attachments because it's a bit buggy with them. For reading email body text, it hasn't failed me yet (knocking on wood).
Once you have the failure notice you can extract the failed address per your prescribed format with a simple regular expression pattern and matching it. Let's assume the body text is already retrieved from the server and you stored it in a stringed named bodyText
using System.Text.RegularExpressions;
// ...
string failedAddressPattern = #"The mail system <(?<address>.+)>";
string capturedAddress = null;
Match match = Regex.Match(bodyText, failedAddressPattern, RegexOptions.IgnoreCase);
if(match.Groups["address"].Success)
{
capturedAddress = match.Groups["address"].Value.Trim();
}
if(capturedAddress == null)
{
// do some form of debug logging here because the pattern no longer works, etc.
}
Beside text scan there is standar for that too, it's called DSN(delivery status notifications, defined in RFC 3464). You can dedect such messages by content-type header "multipart/report; report-type=delivery-status". You can check http://www.lumisoft.ee/lsWWW/download/downloads/Examples/ - it has all you need POP3/IMAP client with examples. It also has MIME message parser what you need, it has also DSN message support. Full soruce code is provided, so getting started should be easy.
I've been following this site with a lot of admiration especially on how questions are professionally answered so I decided to be fully involved.
Please, I need urgent help on a project that I have been working on for a long time but it's almost stalled now just because of a critical issue.
An aspect of the program automates email sending to clients using the free email server systems. Due to the high frequency of email sending, I observed that the email server we're sending to drops larger parts of the emails sent out and literally blocks delivery of major emails to the recipients.
I have tried to reduce the rate of sending email out but to no avail. My fear now is my IP address might have been blocked or may be blocked soon if this continue. The program is not spamming but have to be developed in order to contact a large database of recipients at a goal within short time - like about 1000 or more recipients.
I am using Webbrowser control in C# to automate the process of logging in to the mail server and sending the email out.
Now, what I want is a sample code to use publicly available web proxy servers for each email sent out such that the source IP address appears dynamic and different to the target email server each time a message is sent out to it.
I mean, I want to dynamically get and use free public proxy servers with the Webbrowser control to send out the emails. In this way I believe the email servers would not be able to reject the emails base on the IP address source. I want to know how to dynamically get literally one web proxy server for each email sent, if possible each time.
This project is very critical and this feature is a determinant. I have googled endlessly without any straight forward solution to this issue. I would, therefore, appreciate any useful help, sample codes or resources that could help me to solve this nagging problem once and for all.
Thank you!
Your problem is "free email server systems": they consider you a spammer, and the idea you suggest (spoofing IPs) will, if detected, ruin your reputation.
If you explain what you are trying to accomplish, perhaps someone here can offer a better design.
Are you trying to give people with free email accounts (like Hotmail) bulk-emailing capabilities?
First of all (if I understood your answer right), you don't have to use WebBrowser control - you can use specified .NET solutions that allows you to efficiently sending mails:
MailMessage msg = new MailMessage("from", "to", "subject", "body text");
SmtpClient client = new SmtpClient("smtp server");
System.Net.NetworkCredential cred = new System.Net.NetworkCredential("user", "password");
client.UseDefaultCredentials = false;
client.Credentials = cred;
Client.Send(msg);
Unfortunately, if you want to send e-mails to many recipients and you want to be sure, that these messages reach the recipients - you have to do it using your own e-mail server or do it by purchase the service on a paid e-mail servers - then they will not treat you as a spammer.
But if you anyway want to send e-mails by rotation proxy servers or similar sollution - you can define your proxy:
SmtpClient client = new SmtpClient("my.proxy_server.com", 8080);
First you have to collect any list of available proxy servers which allows you to do it in reasonable time (servers switching can significantly increase total process time because conection time can be different for each proxy server)
Proxy servers list ordered by access time:
http://www.publicproxyservers.com/proxy/list_avr_time1.html
I hate to just post a stack trace here, but I am out of ideas... My app sends emails for various tasks on the website, and 90% of the time there are no problems. However, every so often ASP.NET throws a weird exception, which seems to relate to mail server connectivity (I use google business servers for email). The error is too generic for me to debug, hence the stack trace below. My app captures the exception and writes back a generic 'try again in 5 minutes response'.
I'm stumped by this error because:
Google email is generally very reliable (it is being sent from my domain, not gmail.com).
Volumes are very low, so this shouldn't be a loading/spamming type of problem.
Error is very generic.
Trying again in 5 minutes almost always allows the email to be sent with no problem, with none of the parameters (recipient, subject, body) having changed.
Any ideas? The only outstanding issues I can think of is that:
Email sending is synchronous. This is what I actually want to occur, as I want to respond to the user with a success/failure status message.
I am using Amazon EC2 as a server, if that has any bearing on the matter.
The code:
public static void SendMail(String from, String to, String subject, String body, bool IsHtml)
{
MailMessage m = new MailMessage(from, to, subject, body);
m.IsBodyHtml = IsHtml;
SmtpClient smtpClient = new SmtpClient();
smtpClient.EnableSsl = true;
smtpClient.Send(m);
}
The exception:
System.Net.Mail.SmtpException: Error in processing. The server response was: 4.3.0 Mail server temporarily rejected message. m6sm2190005vcx.24
at System.Net.Mail.DataStopCommand.CheckResponse(SmtpStatusCode statusCode, String serverResponse)
at System.Net.Mail.DataStopCommand.Send(SmtpConnection conn)
at System.Net.Mail.SmtpConnection.OnClose(Object sender, EventArgs args)
at System.Net.ClosableStream.Close()
at System.Net.Mail.MailWriter.Close()
at System.Net.Mail.SmtpClient.Send(MailMessage message)
I've worked on bulk email systems in the past. The exception message you are getting is totally descriptive: that SMTP server is temporarily not accepting mail. This can be due to a number of conditions:
The server is busy
You are sending too many emails too fast (this can make you look like a spammer)
General errors
The fact that retrying the email later always works indicates that this is normal, expected behavior. There is nothing you can do differently to avoid this, it's a common method used by ISPs to throttle traffic when needed.
In addition to what Dave Swersky already said:
You could store the emails you want to send somewhere (like filesystem or database) and let the e-mail generation be handeld by a service. Your service would watch for new emails to send. If an error occurs while sending, you could put the e-mail back into the queue and try again later.
Maybe you can even use a local STMPServer that uses GoogleMail as relay server. It that case you could use the built-in pickupdirectory functionality instead of writing it yourself.
I use C# to send email using System.Net.Mail.
But How can I know whether the email has been sent successfully or fail?
Not a direct answer of course, but here is a great article from Coding Horror about sending emails through code, which addresses your question.
The simple answer is that if it's a detectable failure then SmtpClient.Send will throw an SmtpFailedRecipientsException (it will throw an SmtpException if there is a connection problem).
The long answer is that, for many reasons, you won't necessarily get an exception. This can be because your SMTP server is buffering the sends (or if you have it set to local iis or local directory), or simply because the SMTP server does not support returning those error codes.
Most advertising mailing systems track bouncebacks by setting a valid "from address" and monitoring the inbox for that account. Even that, however, is not foolproof (out of office messages, for example).
I would stick to catching exceptions and leaving the others. If you're not sure if emails are valid, maybe you should send users a code to have them validate their email address.
Considering Emails are fire-and-forget, this can be quite hard. Unless you get an exception, denoting a client-server communication issue due to wrong credentials etc, you have no means of knowing if a mail was sucessfully send (meaning: arrived at the addressee).
I've personally never come across an answer to this as there's not really a way you can grantee mail leaving your location is'nt going to get thrown away as soon as it leaves you. You could maybe try and check the sending mailbox for an NDR (none delivery report) but your not always granted to get one
If you mean sent successfully then as other posters say, if it cannot be sent then you will get an exception. If you actually mean recieved succesfully then that is an entirely different matter. SMTP simply does not have a mechanism to find out if the message has been recieved by the recipient, sometimes you will get an ndr if a server can't deliver other times you won't. You could try and do what spammers do and that is to put some kind of image link in your html email body with a unique identifier in the query string. That would allow you to link someone hitting the image url with the email. However that would only tell you the email had been read if the url was hit, it would not tell you that the email hadn't been recieved becuase the recipient might simply not have allowed images to be displayed in their email client.