I'm creating an application in C#. In this i can create a meeting request that is sent to the user through code and appears in Outlook mail.
The below code is what I am using to send the meeting invitation. It is working fine.
StringBuilder OutlookBody = new StringBuilder();
string textvs = #"BEGIN:VCALENDAR
PRODID:-//Microsoft Corporation//Outlook 10.0 MIMEDIR//EN
VERSION:1.0
BEGIN:VEVENT
LOCATION:" + Location + #"
DTSTART:" + string.Format("DTSTART:{0:yyyyMMddTHHmmssZ}", start) + #"
DTEND:" + string.Format("DTEND:{0:yyyyMMddTHHmmssZ}", end) + #"
DESCRIPTION;ENCODING=QUOTED-PRINTABLE:= " + OutlookBody + #"=0D=0A SUMMARY:" + AppoitmentName + #"
PRIORITY:3
END:VEVENT
END:VCALENDAR";
How can i use the same code to remove outlook meeting request.
I have also checked this answer, but it didn't solve my problem.
In OutLook every appointment/meeting will get a unique Id and a ChangeKey. A new ChangeKey is generated whenever there is a modification done to the meeting. To update an existing meeting you must have the Id and latest ChangeKey.
In your approach, if I am not wrong, you are just constructing an ICAL which is added to the outlook via email. In this case, you will not have the Id and ChangeKey to modify the meeting programatically. I would rather suggest you to change the approach.
If you have Microsoft Exchange the following links will guide. Else, ignore the links.
https://msdn.microsoft.com/en-us/library/office/dn495611(v=exchg.150).aspx
https://msdn.microsoft.com/en-us/library/office/dn495612(v=exchg.150).aspx
You can set the method and status of the meeting by adding these lines:
METHOD: CANCEL
STATUS: CANCELLED
See more here.
Use the following code
StringBuilder OutlookBody = new StringBuilder();
string textvs = #"BEGIN:VCALENDAR
PRODID:-//Microsoft Corporation//Outlook 10.0 MIMEDIR//EN
VERSION:1.0
BEGIN:VEVENT
LOCATION:" + Location + #"
DTSTART:" + string.Format("DTSTART:{0:yyyyMMddTHHmmssZ}", start) + #"
DTEND:" + string.Format("DTEND:{0:yyyyMMddTHHmmssZ}", end) + #"
DESCRIPTION;ENCODING=QUOTED-PRINTABLE:= " + OutlookBody + #"=0D=0A SUMMARY:" + AppoitmentName + #"
PRIORITY:3
METHOD:CANCEL
STATUS:CANCELLED
END:VEVENT
END:VCALENDAR";
And use the following Mime Type
System.Net.Mime.ContentType mimeType = new System.Net.Mime.ContentType("text/calendar; method=CANCEL");
AlternateView alternate = AlternateView.CreateAlternateViewFromString(body, mimeType);
message.AlternateViews.Add(alternate);
I solved this issue by changing some lines in code.
Change method from REQUEST to CANCEL ==> str.AppendLine("METHOD:CANCEL");
Change Status to Cancelled ==> str.AppendLine("STATUS:CANCELLED");
In System.Net.Mime.ContentType contype = newSystem.Net.Mime.ContentType("text/calendar"); change method from REQUEST to CANCEL ==> contype.Parameters.Add("method", "CANCEL");
Related
So i need to get informations such as :
Sender mail address (to later get his Domain profile informations)
Mail subject (which should be the "filepath" minus the "msg" extension anyway).
And then, replying to it just like i would push "ReplyAll" button in Outlook. So the reply needs to get the usual Headers such as "From : ....", "To : ...", "Cc : ..." and so on.
All i need is to change its subject, and delete the address depending on the "FromAddress" of the user that will push the button
I've read a bit here and there, and people are talking about a MailItem, but there's no informations about HOW to get this item or how to build it from a .msg file.
What i have to do comes after a specific user action.
The user is supposed to Drag&Drop the mail into a panel, from there i get its local path.
Thanks for your time !
Edit#1
I managed to find out to get informations and to set a .msg file to a MailItem :
Outlook.Application appOutlook = new Outlook.Application();
var email = (Outlook.MailItem)appOutlook.Session.OpenSharedItem(filepath);
string getCC = "";
string getFrom = ""; // From is never null
string getTo = "";
string getSubject = "";
bool lengthCC = email.CC.HasValue();
bool lengthTo = email.To.HasValue();
bool lengthSubject = email.Subject.HasValue();
if (lengthCC)
{
getCC = email.CC.ToString();
}
// and so on...
//
// Display it in MessageBox to confirm test succeeded :
MessageBox.Show("CC : " + getCC +
"\nFrom : " + getFrom +
"\nTo : " + getTo +
"\nSubject : " + getSubject);
email.Close(Outlook.OlInspectorClose.olDiscard);
Now i just need to build the ReplyAll Body and add headers manually myself i guess...
Edit#2
No need to rewrite Headers apparently, doing so :
Outlook._MailItem reply = email.ReplyAll();
reply.To = getFrom;
reply.CC = getCC;
reply.Body = "SomeReplyMessage" + reply.Body;
reply.Send();
Marshal.ReleaseComObject(appOutlook);
Marshal.ReleaseComObject(email);
Marshal.ReleaseComObject(reply);
But it erased the separator above the original message, i'll find a way to re-add it !!!
Edit#3
And there it is, the so-called "separator" wasn't displaying, because i wasn't re-stating an HTML Body !
So, to keep it you can do this :
reply.BodyFormat = Outlook.OlBodyFormat.olFormatHTML;
string ReplyMessageBody = String.Format("AddSome<br>HTMLCode<br>ThereAndHere<br>ButFinishWith : BodyTag</body>");
reply.HTMLBody = ReplyMessageBody + reply.HTMLBody;
Or simpler if you don't need your reply to be an HTML one :
reply.BodyFormat = Outlook.OlBodyFormat.olFormatHTML;
reply.HTMLBody = "AddSomeReplyMessage" + reply.HTMLBody;
Outlook does not work directly wit MSG files - when you call CreateFromTemplate or even OpenSharedItem, Outlook creates a new item in its default store and imports the MSG or OFT file. It does not expose anything that would you let you figure out that the message came from a file; the item is indistinguishable from an item created directly using CreateItem or MAPIFolder.Items.Add.
See edits on original question for answer !
I'm creating an Outlook Add In, which has a subform. The form has a button on it, through which I would like to generate a mailitem, if the user clicks it. I'd like to auto-populate some info in the email, and then leave it for the user to send at their leisure.
My code looks like the following:
private void btnMailDocNotice_Click(object sender, EventArgs e)
{
string clientInfo = string.Empty;
string matInfo = string.Empty;
string author = string.Empty;
string dType = string.Empty;
string fLocation = string.Empty;
string keyWords = string.Empty;
string docName = string.Empty;
clientInfo = this.mCboClient.Text + " " + lblClient;
matInfo = this.mCboMatter.Text + " " + lblMatter;
author = this.txtAuthor.Text;
dType = this.mCboDocType.Text.ToUpper();
fLocation = this.txtSavePath.Text;
keyWords = this.txtKeyWords.Text;
docName = this.txtDocName.Text;
this.sendDocNotice = true;
this.Hide();
CreateMailItem(clientInfo, matInfo, author, dType, this.operatorCode.ToUpper(), fLocation, keyWords, docName);
this.Show();
}
private void CreateMailItem(string clientInfo, string matInfo, string author, string dType, string profiledBy, string fLocation, string keyWords, string docName)
{
this.DNoticeItem = (Outlook.MailItem)ThisAddIn.myApp.CreateItem(Outlook.OlItemType.olMailItem);
this.DNoticeItem.Subject = "Document: " + docName;
this.DNoticeItem.HTMLBody = "<span style=\"font-family:Calibri; font-size: 11pt;\">KeyWords: " + keyWords + "</span>";
this.DNoticeItem.HTMLBody += "<br />Client: " + clientInfo;
this.DNoticeItem.HTMLBody += "<br />Matter: " + matInfo;
this.DNoticeItem.HTMLBody += "<br />Author: " + author;
this.DNoticeItem.HTMLBody += "<br />Doc Type: " + dtClient;
this.DNoticeItem.HTMLBody += "<br />Profiled by: " + profiledBy;
this.DNoticeItem.HTMLBody += "<br />File://" + fLocation;
this.DNoticeItem.Importance = Outlook.OlImportance.olImportanceNormal;
this.DNoticeItem.Display(false);
}
The problem that I'm running into, is it fires an exception on the mailitem.display function, whether I use true or false (doing a bit of research says that determines if the user can access the main Outlook window or not while the mailitem is open). The exception is a COM Exception of "A dialog box is open. Close it and try again". I've tried hiding the WinForm prior to the function call that creates the mail item, then show it again after the function is exited, but it didn't work. I've tried a version of the code where I use System.Diagnostics.Process.Start() to try and open the file after saving it to disk, and while it doesn't fire an exception from the add in, Outlook prompts the user with a message box of the same message from the ComException. I even tried creating a field to see if the doc notice email should be drafted, and thought to have the code take care of that after a form.close() call, thinking the close call would at least dispose of the dialog box that was locking Outlook, and I still got the same exception.
Is there a way to achieve what I want? Does anyone have any suggestions? I'm kind of stuck at the moment, and would appreciate any help/pointers/suggestions anyone has to offer in this issue. My sincere apologies if this is a duplicative question - I couldn't find a good answer to the question. Thank you in advance for your time.
Firstly, why not display yoru own form modelessly?
Secondly (and this is pretty important) do not use code like the following
this.DNoticeItem.HTMLBody += "<br />Client: " + clientInfo;
Every time you run a line like that, you retrieve HTMLBody, add some stuff to it (making the HTML malformed), then set HTMLBody again and force Outlook to make sense of your (malformed) HTML. This (assuming Outlook can parse and fix your HTML) will result in HTML being returned to be different from what you set it to.
Build the HTML body once using a regular string, and set HTMLBody property only once.
I have a tiny problem with my idea ;)
I want to read som emails from gmail (using Mailkit) and save them into multiple files.
Ok you may think "wtf is going on",... I want to extract the orders via mail and save them as single files for sort off log/protocoll. I think I can handle it better
Properties.Settings.Default.status = "Status: Online";
using (var client = new ImapClient())
{
client.Connect(Properties.Settings.Default.Server, Properties.Settings.Default.Port, true);
client.Authenticate(Properties.Settings.Default.Email, Properties.Settings.Default.Passwort);
client.Inbox.Open(FolderAccess.ReadWrite);
for (int i = 0; i < client.Inbox.Count; i++)
{
var message = client.Inbox.GetMessage(i);
var html = message.HtmlBody;
var text = message.TextBody;
var header = message.Subject + " " + message.From + " " + message.Date + " " + message.MessageId;
File.AppendAllLines(Properties.Settings.Default.pathmail + #"\" + "MailMain.txt", new[] { message.HtmlBody });
string line = File.ReadLines(Properties.Settings.Default.pathmail + #"\" + "MailMain.txt").Skip(i).Take(1).First();
dataGridView1.Rows.Add(message.Subject, message.From, message.Date, message.MessageId);
The MailMain.txt contains every email in gmail line after line, so it canĀ“t be difficult to filter them nicely.
Problem 1:
I need to get (e.g) the first line of the txt file, then create new txt with specific name (Properties.Settings.Default.pathmail). Line after line
For example: copy Line#1 from MailMain.txt to Thisisyourfirstline.txt
copy Line#2 from MailMain.txt to Thisisyoursecondline.txt.
Problem 2:
The body of the email contains a bit of HTML ( < /b>). I need to filter that all. Any suggestions ?
greeetings
I would use the StreamReader and StreamWriter to get and write things line by line. And String.Replace to strip the html tags.
I'm having a bit of an issue with a mix between YUI's AJAX and a YUI Datatable. The AJAX request fires properly and I get back the correct data formatted as:
{NoteId:'" + result.NoteId + "', CreatedOn:'" + result.CreatedOn.ToShortDateString() +
"', UpdatedOn:'" + result.UpdatedOn.ToShortDateString() + "', CreatedBy:'" + result.CreatedBy +
"', NoteContent:'" + result.NoteContent + "'}
These match the table identities properly, and I ripped this formatting from the statement that initially creates the datatable (which works properly). I don't know if I have the 'onSuccess' messed up for my AJAX call or what, and this is my first time touching YUI.
Also, if I manually execute the noteTable.addRow and hard code the data, it works.
Code for the AJAX call and Table Update:
function addNote() {
var noteText = editor.get('element').value;
var id = '<%= Model.Menu.Level1Tab %>'
var lpqId = <%= Model.LpqID %>
var sUrl = "/Lpm/Notes";
var callback = {
success: function(o) {
noteTable.addRow(o.responseText);
},
failure: function(o) {
}
}
var transaction = YAHOO.util.Connect.asyncRequest('POST', sUrl, callback, 'id=' + id + '¬eContent=' + noteText + '¬eId=' + noteId + '&lpqId=' + lpqId);
}
I'm pretty well stuck on this, so if anyone could have a look and let me know where I messed something up, I'd appreciate it. If you need more info, I have plenty, including firebug debugging info.
Thanks in advance for the help
Looks like you need to convert the o.responseText from string to object. The JSON Utility can help you do that: http://developer.yahoo.com/yui/json/.
Incidentally, DataTable's DataSource integration can help manage these issues for you. This example (http://developer.yahoo.com/yui/examples/datatable/dt_xhrjson.html) shows you how to set up a DataSource and integrate it with a DataTable. Note how you can send a request to get some data from your server and then use one of the "onDataReturn..." methods (see "Loading data at runtime" under http://developer.yahoo.com/yui/datatable/#data) in your callback.
We have an app that allows users to send e-mails from our system. It allows the user to specify their e-mail address, and gives them several standard templates to use as a starting point for their e-mail.
When we send the e-mails, we use the address they provided as the 'reply-to', but the 'from' address of the e-mail (naturally) looks like our system (from 'submit#ourserver.com').
Is there a way to change this without getting tangled up in spam filters or automatic blocking? We'd prefer not to confuse the recipient as to who actually composed the e-mail they've received.
I'll refer you to Jeff Atwood's Coding Horror article about sending e-mail programattically. It describes in lengths the steps you should take to prevent your e-mail from being caught in spam filters, etc...
Jeff Atwood's Coding Horror: So You'd Like to Send Some Email (Through Code)
I use this code:
public static bool sendEmail(string fromName, string fromEmail, string body, string subject, string toEmail) {
String strReplyTo = fromEmail.Trim();
String strTo = toEmail;
String msgBodyTop = "Email from: " + #fromName + "(" + #fromEmail + ")\n"
+ "" + " " + DateTime.Now.ToLongTimeString()
+ " FROM " + HttpContext.Current.Request.Url.ToString + " : \n\n"
+ "---\n";
MailMessage theMail = new MailMessage(fromEmail, strTo, subject, msgBodyTop + body);
theMail.From = new MailAddress(strReplyTo, fromName);
SmtpClient theClient = new SmtpClient(ConfigurationManager.AppSettings["SMTP"].ToString());
theClient.Send(theMail);
return true;
}
It seems to work for me...
After discussing with our ops people and trying Atomiton's method, I've found that this is not actually possible for us.