How to use the Google Contacts API through Oauth2 authentication

I have this code below to get calendar entries using the Google Calendar API ( https://developers.google.com/google-apps/calendar/ ) that uses OAuth2. It works well.

private IList<string> scopes = new List<string>(); private CalendarService calendarService; private void InitializeCalendarService() { // Add the calendar specific scope to the scopes list scopes.Add(CalendarService.Scopes.Calendar.GetStringValue()); // Display the header and initialize the sample CommandLine.EnableExceptionHandling(); CommandLine.DisplayGoogleSampleHeader("Google.Api.Calendar.v3 Sample"); // Create the authenticator //FullClientCredentials credentials = PromptingClientCredentials.EnsureFullClientCredentials(); var provider = new NativeApplicationClient(GoogleAuthenticationServer.Description); FullClientCredentials credentials = new FullClientCredentials(); credentials.ClientId = "XYZ.apps.googleusercontent.com"; credentials.ClientSecret = "XYZ"; credentials.ApiKey = "XYZ"; provider.ClientIdentifier = credentials.ClientId; provider.ClientSecret = credentials.ClientSecret; OAuth2Authenticator<NativeApplicationClient> auth = new OAuth2Authenticator<NativeApplicationClient>(provider, GetAuthorization); // Create the calendar service using an initializer instance BaseClientService.Initializer initializer = new BaseClientService.Initializer(); initializer.Authenticator = auth; calendarService = new CalendarService(initializer); CalendarList list = calendarService.CalendarList.List().Execute(); // do something with the list .. the list is all good } public IAuthorizationState GetAuthorization(NativeApplicationClient client) { // You should use a more secure way of storing the key here as // .NET applications can be disassembled using a reflection tool. const string STORAGE = "google.samples.dotnet.calendar"; const string KEY = "s0mekey"; // Check if there is a cached refresh token available. IAuthorizationState state = AuthorizationMgr.GetCachedRefreshToken(STORAGE, KEY); if ((state != null)) { try { client.RefreshToken(state); return state; // we are done } catch (DotNetOpenAuth.Messaging.ProtocolException ex) { CommandLine.WriteError("Using an existing refresh token failed: " + ex.Message); CommandLine.WriteLine(); } } // Retrieve the authorization from the user string[] array = new string[scopes.Count]; scopes.CopyTo(array,0); state = AuthorizationMgr.RequestNativeAuthorization(client, array); AuthorizationMgr.SetCachedRefreshToken(STORAGE, KEY, state); return state; } 

How can I use a similar OAuth2Authenticator to retrieve contacts?

I can get contacts using the code below, but not without a password, I need to get it to work using Oath2. The example below uses the contacts Gdata api v2. I can see that I can go through the OAuth2Authenticator, but I don’t know exactly how to do it correctly (I can’t see valid C # examples on google) and get an access code based on what the user selects. I can't figure out how to use OAuth2Authenticator with api v3 contacts ( https://developers.google.com/google-apps/contacts/v3/ )

 RequestSettings rsLoginInfo = new RequestSettings("", email,pwd); rsLoginInfo.AutoPaging = true; ContactsRequest cRequest = new ContactsRequest(rsLoginInfo); // fetch contacts list Feed<Contact> feedContacts = cRequest.GetContacts(); foreach (Contact gmailAddresses in feedContacts.Entries) { // Looping to read email addresses foreach (EMail emailId in gmailAddresses.Emails) { lstContacts.Add(emailId.Address); } } 
+4
source share
2 answers

I ended up extracting the access code using a browser control that reads the value of the document title when the user selects the google account and grants access.

eg:

Generate url

 RedirectURI = "urn:ietf:wg:oauth:2.0:oob" OAuth2Parameters parameters = new OAuth2Parameters() { ClientId = clientId, ClientSecret = clientSecret, RedirectUri = redirectUri, Scope = requiredScope }; // Request authorization from the user (by opening a browser window): string url = OAuthUtil.CreateOAuth2AuthorizationUrl(parameters); var loginUri = new Uri(url); // This form has browser control GoogleLoginForm form = new GoogleLoginForm(loginUri, redirectUri); var dr = form.ShowDialog(); if (dr == System.Windows.Forms.DialogResult.OK) { parameters.AccessCode = form.OAuthVerifierToken; } 

Then in GoogleLoginForm: We have browser control and the registered browserControl_Navigated event, and do the following. The DocumentTitle contains an access code that is used to generate a token.

 private void GoogleLoginForm_Load(object sender, EventArgs e) { wbGoogleLogin.Url = _loginUri; } private void wbGoogleLogin_Navigated(object sender, WebBrowserNavigatedEventArgs e) { string fullPath = e.Url.ToString(); WebBrowser control = sender as WebBrowser; if (control != null && !string.IsNullOrEmpty(control.DocumentTitle) && control.DocumentTitle.Contains("Success code")) { _OAuthVerifierToken = control.DocumentTitle.Replace("Success code=",""); DialogResult = DialogResult.OK; } } 

Thus, this can be done in the same piece of code, without having to write a complex callback service to read the access token back into our system.

It’s not entirely clear why this is built into the api calendar, but the contacts API is not.

+4
source

Firstly, a quick answer to your question. I believe that IAuthorizationState has similar properties for OAuth2Parameters. So you should do it (combining it with the code you have for the calendar):

 OAuth2Authenticator<NativeApplicationClient> auth = new OAuth2Authenticator<NativeApplicationClient>(provider, GetAuthorization); //This will call your GetAuthorization method auth.LoadAccessToken() RequestSettings settings = new RequestSettings("appName", auth.State.AccessToken); ContactsRequest cRequest = new ContactsRequest(settings); // fetch contacts list Feed<Contact> feedContacts = cRequest.GetContacts(); foreach (Contact gmailAddresses in feedContacts.Entries) { // Looping to read email addresses foreach (EMail emailId in gmailAddresses.Emails) { lstContacts.Add(emailId.Address); } } 

This should work, as RequestSettings allows you to specify an access token. However, I myself prefer to use:

 var parameters = new OAuth2Parameters() { //Client ClientId = CLIENT_ID, ClientSecret = CLIENT_SECRET, RedirectUri = redirectUri, Scope = "https://www.google.com/m8/feeds", ResponseType = "code" }; //User clicks this auth url and will then be sent to your redirect url with a code parameter var authorizationUrl = OAuthUtil.CreateOAuth2AuthorizationUrl(parameters); . . . //using the code parameter parameters.AccessCode = code; OAuthUtil.GetAccessToken(parameters); var settings = new RequestSettings(applicationName, parameters); var cr = new ContactsRequest(settings); //Now you can use contacts as you would have before 

Although, Ive only tested this with web server applications, so maybe an authenticator is needed for your situation? I found these source codes handy:

OAuth2Demo

IAuthorizationState

OAuth2Authenticator

+2
source

Source: https://habr.com/ru/post/1497349/


All Articles