MailChimp.Net User is not subscribed - asp.net

I'm trying to call MailChimp Subscribe with MailChimp.Net NuGet package to add user to list in MailChimp.
The request is performed with success as far as I can see from MailChimp dashboard but the user is not subscribed in the list.
Did anyone faced such issue?
var myMergeVars = new MergeVar();
myMergeVars.Add("FNAME", "Testy");
myMergeVars.Add("LNAME", "Testerson");
var mc = new MailChimpManager("MYKEY");
// Create the email parameter
var email = new EmailParameter()
{
Email = "test.spektor#gmail.com"
};
EmailParameter results = mc.Subscribe("LISTID", email);

The request should be made with doubleOptIn: false option, otherwise user will receive an email with confirmation on his email box.
var result = mc.Subscribe(listId, emailParameter, myMergeVars, doubleOptIn: false, updateExisting: true);

Related

Google event attendees list not updating on Outlook calendar event

I am writing a calendar integration and using the Google Calendar api and Outlook Graph api to sync calendar events. I am receiving webhooks as changes are made to events, so it is important that events are identical across calendar providers.
When I update the event attendees on a Google event however, an event update is not sent to Outlook attendees. The result is that Outlook attendees do not have an accurate attendee list.
If I change the Title/Description/Time, Google sends an event update and the Google and Outlook events get synced (the Outlook event is updated with the correct attendee list).
I have tried updating fields the user doesn't see (ex: sequence, extended properties) in hopes that the change would trigger an event update from Google but that doesn't seem to work.
Has anyone found a way to trigger a Google event update when attendees are added or removed?
UPDATE:
For Outlook users, I create a subscription (using the graph SDK) to each user’s calendar:
var graphClient = await MicrosoftAuthenticationProvider.GetGraphClient(CALENDAR_CLIENT_ID, CALENDAR_CLIENT_SECRET, CALENDAR_REDIRECT_URI, CALENDAR_ACCESS_SCOPES, RefreshToken).ConfigureAwait(false);
var tmpSubscription = new Subscription
{
ChangeType = WEBHOOK_SUBSCRIPTION_CHANGETYPE,
NotificationUrl = WEBHOOK_NOTIFICATION_ENDPOINT,
Resource = WEBHOOK_EVENT_RESOURCE_NAME,
ExpirationDateTime = maxSubscriptionLength,
ClientState = clientState
};
var subscription = await graphClient.Subscriptions
.Request()
.AddAsync(tmpSubscription)
.ConfigureAwait(false);
When an Outlook event is updated, my webhook notification endpoint receives a notification from Outlook. This happens successfully when I edit the summary, description, start or end of an event in Google. It does not happen when I add or remove attendees.
To replicate: create an event in Google that has an attendee that uses Outlook. You will see the event in Outlook. Add another attendee to the Google event. Google does not send Outlook an update email (the way it does if the title/time/description changes). The Google and Outlook events attendees are now different.
I found a work-around:
If I know the attendees have changed, I am changing the description of the event and sending a silent patch request to Google:
var tmpEvent = new Google.Apis.Calendar.v3.Data.Event
{
Description = Event.Description + "---attendees updated---",
};
//don't send the notification to anyone
//all attendees will get the notification when we resave the event with the original description
var patchRequest = service.Events.Patch(tmpEvent, GOOGLE_PRIMARY_CALENDARID, ExternalID);
patchRequest.SendUpdates = EventsResource.PatchRequest.SendUpdatesEnum.None;
await patchRequest.ExecuteAsync().ConfigureAwait(false);
For the patch, setting SendUpdates to None means attendees won’t receive a notification about the change, so all calendar events will be updated silently.
Finally, I save the entire event (with the proper description and attendees) and send the updates to all of the attendees:
var tmpEvent = new Google.Apis.Calendar.v3.Data.Event
{
Id = ExternalID == null ? Convert.ToString(Event.ID) : ExternalID,
Start = new EventDateTime
{
DateTime = Event.StartDate,
TimeZone = GetGoogleTimeZoneFromSystemTimeZone(timeZoneInfo.Id)
},
End = new EventDateTime
{
DateTime = Event.EndDate,
TimeZone = GetGoogleTimeZoneFromSystemTimeZone(timeZoneInfo.Id)
},
Summary = Event.Title,
Description = Event.Description,
Attendees = attendees.Select(a => new EventAttendee
{
Email = a.Value,
ResponseStatus = "accepted"
}).ToList(),
GuestsCanInviteOthers = false,
Location = Event.Location
};
var updateRequest = service.Events.Update(tmpEvent, GOOGLE_PRIMARY_CALENDARID, ExternalID);
updateRequest.SendUpdates = EventsResource.UpdateRequest.SendUpdatesEnum.All;
savedEvent = await updateRequest.ExecuteAsync().ConfigureAwait(false);
This isn't ideal because it requires two calls to Google's API just to properly save the attendees, but on the plus side, attendees are only notified of the change once.

Initiate Appmaker Document Approval from Google Drive

I've customized Document Management System template in Appmaker as per my needs. Now instead of going to Appmaker every time to initiate an approval I want to provide functionality to initiate the workflow from Google Drive.So users can select file for Approval directly from Google Drive.
My question is is there any Rest call or something via which I can initiate DMS workflow from Third party app?
Well I found a way out to achieve the result.
Steps:
Drive API provides a way to add your App in 'Open With' menu in Google Drive.
So I've created my custom app and deployed it. This app will simply receive params from Google Drive 'Open with' menu and pass it to Appmaker Document Approval System.
In Appmaker Create request page parse if request contains these params, if yes then select files using these params.
This way my users can initiate the Document Approval Workflow from Google Drive.
References :
How to add/list your App in Google Drive
Step by Step video guideline to Create and publish your App
Code:
'Open With' App code for redirecting users from Google Drive to Appmaker.
code.gs:
var AUTHORIZE_URL = 'https://accounts.google.com/o/oauth2/auth';
var TOKEN_URL = 'https://accounts.google.com/o/oauth2/token';
var REDIRECT_URL= ScriptApp.getService().getUrl();
var tokenPropertyName = 'GOOGLE_OAUTH_TOKEN';
var CLIENT_ID = 'your client id';
var CLIENT_SECRET = 'your client secrect';
function doGet(e) {
var HTMLToOutput;
if(e.parameters.state){
var state = JSON.parse(e.parameters.state);
if(state.action === 'create'){
HTMLToOutput = "<html><h1>Creation Of Docs Not supported by this App!</h1></html>";
}
else {
var id = state.exportIds;
var file = DriveApp.getFileById(id);
//append params to your appmaker URL
var url = 'yourappmaker published url'+'?param1='+file.getName()+'&param2='+file.getUrl()+'#AddRequest';
HTMLToOutput = HtmlService.createHtmlOutput('<html><script>'
+'window.close = function(){window.setTimeout(function(){google.script.host.close()},9)};'
+'var a = document.createElement("a"); a.href="'+url+'"; a.target="_blank";'
+'if(document.createEvent){'
+' var event=document.createEvent("MouseEvents");'
+' if(navigator.userAgent.toLowerCase().indexOf("firefox")>-1){window.document.body.append(a)}'
+' event.initEvent("click",true,true); a.dispatchEvent(event);'
+'}else{ a.click() }'
+'close();'
+'</script>'
// Offer URL as clickable link in case above code fails.
+'<body style="word-break:break-word;font-family:sans-serif;">Failed to open automatically. Click here to proceed.</body>'
+'<script>google.script.host.setHeight(40);google.script.host.setWidth(410)</script>'
+'</html>')
.setWidth( 90 ).setHeight( 1 );
}
}
else if(e.parameters.code){//if we get "code" as a parameter in, then this is a callback. we can make this more explicit
getAndStoreAccessToken(e.parameters.code);
HTMLToOutput = '<html><h1>App is installed, you can close this window now or navigate to your Google Drive.</h1></html>';
}
else {//we are starting from scratch or resetting
HTMLToOutput = "<html><h1>Install this App into your Google Drive!</h1><a href='"+getURLForAuthorization()+"'>click here to start</a></html>";
}
console.log(getURLForAuthorization());
return HtmlService.createHtmlOutput(HTMLToOutput);
}
function getURLForAuthorization(){
return AUTHORIZE_URL + '?response_type=code&client_id='+CLIENT_ID+'&redirect_uri='+REDIRECT_URL +
'&scope=https://www.googleapis.com/auth/drive.install https://www.googleapis.com/auth/userinfo.email';
}
function getAndStoreAccessToken(code){
var parameters = { method : 'post',
payload : 'client_id='+CLIENT_ID+'&client_secret='+CLIENT_SECRET+'&grant_type=authorization_code&redirect_uri='+REDIRECT_URL+'&code=' + code};
var response = UrlFetchApp.fetch(TOKEN_URL,parameters).getContentText();
var tokenResponse = JSON.parse(response);
UserProperties.setProperty(tokenPropertyName, tokenResponse.access_token);
}
function getUrlFetchOptions() {
return {'contentType' : 'application/json',
'headers' : {'Authorization' : 'Bearer ' + UserProperties.getProperty(tokenPropertyName),
'Accept' : 'application/json'}};
}
//naive check, not using for now, use refresh tokens and add proper checking
function isTokenValid() {
return UserProperties.getProperty(tokenPropertyName);
}
In Document workflow 'Create Request' page, add event to onAttach() method. Write below function,
//client side
function checkIfRedirected(widget)
{
// console.log(location.origin);
google.script.url.getLocation(function(location) {
var params = location.parameter;
var param1 = params.param1;
var param2 = params.param2;
widget.datasource.item.DocumentName = param1;
widget.datasource.item.DocumentUrl = param2;
widget.datasource.item.Owner = app.user.email;
});
}

onCreate send email to self in AppMaker?

Still learning about app maker and found this presentation at Google I/O '17 "Build Powerful Custom Apps Fast with App Maker on G Suite"
At timestamp 15.24 sec some code is shown on the screen showing how to send an email to yourself once someone creates a new item can.
https://youtu.be/Q84HQgI3Dd8?t=15m27s
Question
Can anyone advise where and how this code can be implemented its pretty cool and would be a great feature to add when a record is created
Thanks in advance and no worries if you cant help
You are looking for model events:
https://developers.google.com/appmaker/models/events
In App Maker models typically have onCreate, onSave, onLoad, onDelete events. It is the best place to handle email notifications. Here is a link to App Script email API:
https://developers.google.com/apps-script/reference/mail/mail-app
I strongly recommend you to go to the Codelab for App Maker. The section Building a form to send an email describes the whole process.
The steps to highlight are:
Step 11 - Set the onClick property of the button as a custom action with the code:
var widgets = widget.parent.descendants;
var to = widgets.To.value;
var subject = widgets.Subject.value;
var msg = widgets.Msg.value;
widgets.EmailStatus.text = 'Sending email...';
SendEmail(to, subject, msg)
Step 13 - Add the following ClientScript code:
function clearEmailForm(){
var formWidgets = app.pages.Basic.descendants;
formWidgets.EmailStatus.text = "";
formWidgets.Msg.value = "";
formWidgets.To.value = "";
formWidgets.Subject.value = "";
}
function SendEmail(To, Subject, Msg){
var status = app.pages.Basic.descendants.EmailStatus;
google.script.run.withSuccessHandler(function(result) {
status.text = 'Email sent...';
clearEmailForm();
})
.SendEmail(To, Subject, Msg);
}
Step 14 - Now add the corresponding code to the ServerScript.
function SendEmail(to, subject, msg){
MailApp.sendEmail(to, subject , msg);
}

How to post on my facebook page from my website using Facebook App keys created from my facebook account?

Below is the code i am using to achieve this functionality, and i have successfully posted it to my facebook wall from my website but i am not able to post to my facebook page?
How can i get page access token using FaceBookClient() in c# SDK?
var client = new FacebookClient();
dynamic token = client.Get("oauth/access_token", new
{
client_id = ConfigurationManager.AppSettings["FacebookAPI"].ToString(),
client_secret = ConfigurationManager.AppSettings["FacebookAPIKey"].ToString(),
grant_type = "client_credentials"
});
client.AccessToken = token.access_token;
dynamic parameters = new ExpandoObject();
parameters.title = detail.Title;
parameters.message = GetDescription(detail.Description, detail.Content);
parameters.link = "http://test.com/blog" + detail.RelativeLink;//HttpContext.Current.Request.IsLocal ? "http://test.com/blog" + detail.RelativeLink : HttpContext.Current.Request.Url.Authority + "" + detail.RelativeLink;
var result = client.Post(ConfigurationManager.AppSettings["FacebookPageID"].ToString() + "/feed", parameters);
Please read the docs at
https://developers.facebook.com/docs/graph-api/reference/v2.3/page/feed#publish
It's clear that you can't use an App Access Token for posting to a Page, because a Post always needs to be related to a profile.
A user access token with publish_actions permission can be used to publish new posts on behalf of that person. Posts will appear in the voice of the user.
A page access token with publish_pages permission can be used to publish new posts on behalf of that page. Posts will appear in the voice of the page.

Firebase user counter

I'm trying to display the amount of users that are currently viewing my page using firebase and shopify's API. Haven't been able to find any documentation.
You could implement a presence system - see this Firebase blog post.
When a user logs in,
Authenticate the user
Set the onDisconnect listener to remove the presence object (#3) when the user disconnects.
Set the user's presence ref to true
Example (from blog post)
var amOnline = new Firebase('https://<demo>.firebaseio.com/.info/connected');
var userRef = new Firebase('https://<demo>.firebaseio.com/presence/' + userid);
amOnline.on('value', function(snapshot) {
if (snapshot.val()) {
userRef.onDisconnect().remove();
userRef.set(true);
}
});

Resources