Upon Approve or Reject I execute custom email notification that goes like this:
public void Process(WorkflowPipelineArgs args)
{
Assert.ArgumentNotNull(args, "args");
ProcessorItem processorItem = args.ProcessorItem;
if (processorItem != null)
{
//all variables get initialized
var site = Sitecore.Configuration.Factory.GetSite("website");
string contentPath = args.DataItem.Paths.ContentPath;
var contentItem = args.DataItem;
var contentWorkflow = contentItem.Database.WorkflowProvider.GetWorkflow(contentItem);
var contentHistory = contentWorkflow.GetHistory(contentItem);
var status = "Approved";
//Get the item from the master database
var workflowItem = Sitecore.Context.ContentDatabase.Items[args.DataItem.ID];
//Get the workflow history so that we can email the last person in that chain.
if (contentHistory.Length > 0)
{
//submitting user (string)
string lastUser = contentHistory[contentHistory.Length - 1].User;
//sitecore user (so we can get email address)
var submittingUser = Sitecore.Security.Accounts.User.FromName(lastUser, false);
//approve/reject comments
var comments = args.Comments;
StringBuilder messageBody = new StringBuilder();
messageBody.AppendFormat("<div style='font-weight:bold'>Domain: {0}</div>", site.HostName);
messageBody.AppendLine();
messageBody.AppendFormat("<div style='font-weight:bold'>Content Item: {0}</div>", contentItem.Paths.FullPath);
messageBody.AppendLine();
messageBody.AppendFormat("<div style='font-weight:bold'>Status: {0}</div>", status);
messageBody.AppendLine();
messageBody.AppendFormat("<div style='font-weight:bold'>Approver Comments: {0}</div>", comments);
MailMessage msg = new MailMessage(FromAddress, submittingUser.Profile.Email);
msg.Subject = string.Format("{0} - Content item has been approved", site.HostName);
msg.Body = messageBody.ToString();
SmtpClient smtpClient = new SmtpClient(MailServer);
smtpClient.Send(msg);
}
}
}
Problem: I can currently get the reviewer comments but I cant figure out how to get the name or email of the reviewer.
Any Ideas?
Thanks,
C
Sitecore.Context.User should give you access to the user who clicked the button, which seems to be what you're looking for.
Related
HI I am trying to use Microsoft graph api to send messages.
Previously, I was sending messages/emails with the graph api without attachment. Now I need to attach 10 attachment each.
So I looked for examples and got to the Microsoft document and it shows the following code
GraphServiceClient graphClient = new GraphServiceClient( authProvider );
var attachment = new FileAttachment
{
Name = "smile",
ContentBytes = Convert.FromBase64String("R0lGODdhEAYEAA7")
};
await graphClient.Me.Messages["{message-id}"].Attachments
.Request()
.AddAsync(attachment);
Link:
https://learn.microsoft.com/en-us/graph/api/message-post-attachments?view=graph-rest-1.0&tabs=csharp
My question is what it is showing is not clear I am not sure I would I use message-id. Also I dont see if the Message is created and how the attachment is created.
Can someone help please.
You may refer to this document to learn the example about how to send email with attachments. And the below is my test code, it worked for me, I used client credential flow to provide authentication..
using Azure.Identity;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Graph;
public class HomeController : Controller
{
private readonly IWebHostEnvironment _appEnvironment;
public HomeController(IWebHostEnvironment appEnvironment)
{
_appEnvironment = appEnvironment;
}
public async Task<string> sendMailAsync() {
var scopes = new[] { "https://graph.microsoft.com/.default" };
var tenantId = "your_tenant_name.onmicrosoft.com";
var clientId = "azure_ad_clientid";
var clientSecret = "client_secret";
var clientSecretCredential = new ClientSecretCredential(
tenantId, clientId, clientSecret);
var graphClient = new GraphServiceClient(clientSecretCredential, scopes);
var a = _appEnvironment.WebRootPath;//I have a file stored in my project
var file = a + "\\hellow.txt";
byte[] fileArray = System.IO.File.ReadAllBytes(#file);
//string base64string = Convert.ToBase64String(fileArray);
var message = new Message
{
Subject = "Meet for lunch?",
Body = new ItemBody
{
ContentType = BodyType.Text,
Content = "The new cafeteria is open."
},
ToRecipients = new List<Recipient>()
{
new Recipient
{
EmailAddress = new EmailAddress
{
Address = "xxx#outlook.com"
}
}
},
Attachments = new MessageAttachmentsCollectionPage()
{
new FileAttachment
{
Name = "attachment.txt",
ContentType = "text/plain",
ContentBytes = fileArray
}
}
};
await graphClient.Users["user_id"]
.SendMail(message, null)
.Request()
.PostAsync();
return "success";
}
}
I am trying to get a script running that takes multiple file IDs from a Google Sheet and attaches them to an email. I cannot get multiple files to be attached using DriveApp.getFileById.
The script runs and fires off an email, but with no attachments.
function createAndSendDocument(values) {
// Get the email address of the active user
var email = Session.getActiveUser().getEmail();
// Get the name of the document to use as an email subject line.
var subject = 'New Paperwork';
//Let's add the attachments variables
var attachmentstring = values["Which documents do you want to attach?"];
var array = attachmentstring.toString().split(",");
var blobs = [];
var x = 0;
for (var i = 0; i < array.length; i++) {
//check if even
if (i % 2 === 0) {
blobs[x] = array[i];
x++;
}
}
// Append a new string to the "url" variable to use as an email body.
var body = 'your doc: ' + blobs[0] + blobs[1] + array[0] + array[1] + "length:" + array.length;
// Send yourself an email with a link to the document.
GmailApp.sendEmail(email, subject, body, {attachments: blobs});
}
I edited the original post to include the snippet of code. Here is the output of the blobs and array.
undefinedundefinedW-4 2019.pdf1YjQqFNze8VX0L6wZ9O3Y9AJNznR8jfxqlength:4
This code worked:
function createAndSendDocument(values) {
// Get the email address of the active user
var email = Session.getActiveUser().getEmail();
// email subject line.
var subject = 'New Paperwork';
// add the attachments variables
var attachmentstring = values["Which documents do you want to attach?"];
var array = attachmentstring.toString().split(",");
var blobs = [];
var x = 0;
for (var i = 0; i < array.length; i++) {
//check if even
if (i % 2 === 0) {
}
else
{
blobs[x] = DriveApp.getFileById(array[i]).getBlob();
x++;
}
}
// an email body.
var body = 'Hello';
// Send an email with attachments
GmailApp.sendEmail(email, subject, body, {attachments: blobs});
}
We are creating an app that is meant to be used with a Service Account in your system; another user (user-2) has authorized this app by adding our app key to their Custom Application list. How do I get this User-2's UserID, so we can impersonate him and access his files list and files, etc. We need their UserID, so we can pass the "AS-User: " Header. And can this header be set using some property from within the .NET SDK - a sample code will be appreciated.
This does it for all enterprise users but you can easily put an if statement to get the user you're looking for.
static async Task MainAsync()
{
// rename the private_key.pem.example to private_key.pem and put your JWT private key in the file
var privateKey = File.ReadAllText(PRIVATE_KEY_FILE);
var boxConfig = new BoxConfig(CLIENT_ID, CLIENT_SECRET, ENTERPRISE_ID, privateKey, JWT_PRIVATE_KEY_PASSWORD, JWT_PUBLIC_KEY_ID);
var boxJWT = new BoxJWTAuth(boxConfig);
var adminToken = boxJWT.AdminToken();
Console.WriteLine("Admin Token: " + adminToken);
Console.WriteLine();
var adminClient = boxJWT.AdminClient(adminToken); // adminClient == serviceAccount
var userDetails = await adminClient.UsersManager.GetCurrentUserInformationAsync();
Console.WriteLine("\tAdmin User Details:");
Console.WriteLine("\tId: {0}", userDetails.Id);
Console.WriteLine("\tName: {0}", userDetails.Name);
Console.WriteLine("\tStatus: {0}", userDetails.Status);
Console.WriteLine();
var users = await adminClient.UsersManager.GetEnterpriseUsersAsync();
users.Entries.ForEach(i =>
{
Console.WriteLine("\t{0}", i.Name);
Console.WriteLine("\t{0}", i.Status);
if (i.Status == "active")
{
var userToken = boxJWT.UserToken(i.Id);
var userClient = boxJWT.UserClient(userToken, i.Id);
Task u = getUserItems(userClient, i.Id);
u.Wait();
}
});
}
static async Task getUserItems(BoxClient userClient, string id)
{
var userDetails = await userClient.UsersManager.GetCurrentUserInformationAsync();
Console.WriteLine("\nManaged User Details:");
Console.WriteLine("\tId: {0}", userDetails.Id);
Console.WriteLine("\tName: {0}", userDetails.Name);
Console.WriteLine("\tStatus: {0}", userDetails.Status);
Console.WriteLine();
Console.WriteLine("managed users older items");
var items = await userClient.FoldersManager.GetFolderItemsAsync("0", 500);
items.Entries.ForEach(i =>
{
Console.WriteLine("\t{0}", i.Name);
});
Console.WriteLine();
}
I am attempting to set a simple reminder email to a technician to remind when a routine service is due. I have a 2d array and code that works, but it only sends 1 email, which is the lowest row.
I'm kinda new to this, but I would like it to run through each row and send a reminder for every overdue.
Any help appreciated.
This is what I have now:
function Email_Reminder()
{;
var sheet = SpreadsheetApp.getActiveSheet();
statusArray = sheet.getDataRange().getValues();
status = "overdue";
for (i=3;i < statusArray.length;i++){
if (status == statusArray[i][6]) {
var customer = statusArray[i][0];
}
}
var email = "djens12#gmail.com"
var subject = "Reminder";
var body = "This is a reminder that the service is overdue for " +customer+ "";
MailApp.sendEmail(email,subject,body,{NoReply : true});
}
thanks
Just move your MailApp.sendEmail() inside your for loop
function Email_Reminder()
{;
var sheet = SpreadsheetApp.getActiveSheet();
statusArray = sheet.getDataRange().getValues();
status = "overdue";
var email = "djens12#gmail.com"
var subject = "Reminder";
for (i=3;i < statusArray.length;i++){
if (status == statusArray[i][6]) {
var customer = statusArray[i][0];
var body = "This is a reminder that the service is overdue for " +customer+ "";
MailApp.sendEmail(email,subject,body,{NoReply : true});
}
}
}
asp.net mvc 2
I have this action in Identity controller
public ActionResult Details(string id, MessageUi message)
{
And I'm trying to redirect to this action from another controller, but I don't know how should I pass the message parameter
I was trying with
var id = "someidvalue"
var message = new MessageUi("somevalue");
return RedirectToAction("Details", "Identity", new { id, message});
}
but message parameter is null
That's normal. You cannot pass complex objects in urls when redirecting and that's the reason why the MessageUi object is not received. Only scalar properties which will be translated into &-separated key/value pairs in the url.
One possibility would be to pass all the simple properties of this object so that the default model binder can reconstruct it at the target location:
var id = "someidvalue"
var message = new MessageUi("somevalue");
return RedirectToAction("Details", "Identity", new {
id = id,
MessageProp1 = message.MessageProp1,
MessageProp2 = message.MessageProp2,
MessageProp3 = message.MessageProp3,
});
You could also pass only a message id:
var id = "someidvalue";
return RedirectToAction("Details", "Identity", new {
id = id,
messageId = "somevalue"
});
and have the message object being reconstructed in the details action using this id:
public ActionResult Details(string id, string messageId)
{
var message = new MessageUi(messageId);
...
}
and this job could be greatly done by a custom model binder for the MessageUi type.
Another possibility would be to use TempData or Session:
var id = "someidvalue";
TempData["message"] = new MessageUi("somevalue");
return RedirectToAction("Details", "Identity", new { id });
and then inside the Details action:
var message = TempData["message"] as MessageUi;