Функции утилиты Gmail
Работа с запросом FreeBusy
Aspose.Email предоставляет механизм запроса для проверки, является ли какое-либо событие назначенным или нет в соответствии с критериями. Для этой цели предоставлен класс FreebusyQuery, который позволяет подготовить запрос для конкретного календаря.
Запрос календаря
Этот пример кода демонстрирует функцию запроса календаря. В этом примере выполняются следующие задачи:
- Создание и вставка календаря
- Создание события
- Вставка события
- Подготовка FreeBusyQuery
- Получение FreebusyResponse
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
// Use the GoogleUser and GoogleOAuthHelper classes below to receive an access token
using (IGmailClient client = GmailClient.GetInstance(accessToken, user.Email))
{
// Initialize calendar item
Aspose.Email.Clients.Google.Calendar calendar1 = new Aspose.Email.Clients.Google.Calendar("summary - " + Guid.NewGuid().ToString(), null, null, "Europe/Kiev");
// Insert calendar and get back id of newly inserted calendar and Fetch the same calendar using calendar id
string id = client.CreateCalendar(calendar1);
Aspose.Email.Clients.Google.Calendar cal1 = client.FetchCalendar(id);
string calendarId1 = cal1.Id;
try
{
// Get list of appointments in newly inserted calendar. It should be zero
Appointment[] appointments = client.ListAppointments(calendarId1);
if (appointments.Length != 0)
{
Console.WriteLine("Неправильное количество встреч");
return;
}
// Create a new appointment and Calculate appointment start and finish time
DateTime startDate = DateTime.Now;
DateTime endDate = startDate.AddHours(1);
// Create attendees list for appointment
MailAddressCollection attendees = new MailAddressCollection();
attendees.Add("user1@domain.com");
attendees.Add("user2@domain.com");
// Create appointment
Appointment app1 = new Appointment("Location - " + Guid.NewGuid().ToString(), startDate, endDate, "user2@domain.com", attendees);
app1.Summary = "Summary - " + Guid.NewGuid().ToString();
app1.Description = "Description - " + Guid.NewGuid().ToString();
app1.StartTimeZone = "Europe/Kiev";
app1.EndTimeZone = "Europe/Kiev";
// Insert the newly created appointment and get back the same in case of successful insertion
Appointment app2 = client.CreateAppointment(calendarId1, app1);
// Create Freebusy query by setting min/max timeand time zone
FreebusyQuery query = new FreebusyQuery();
query.TimeMin = DateTime.Now.AddDays(-1);
query.TimeMax = DateTime.Now.AddDays(1);
query.TimeZone = "Europe/Kiev";
// Set calendar item to search and Get the reponse of query containing
query.Items.Add(cal1.Id);
FreebusyResponse resp = client.GetFreebusyInfo(query);
// Delete the appointment
client.DeleteAppointment(calendarId1, app2.UniqueId);
}
finally
{
// Delete the calendar
client.DeleteCalendar(cal1.Id);
}
}
Создание проекта в Google Developer Console
Для пользователя с учетной записью Gmail необходимо создать проект в Google Developer Console. На странице API и аутентификация -> Учетные данные проекта Google необходимо записать информацию, такую как идентификатор клиента и секрет клиента. Эта информация вместе с именем пользователя и паролем учетной записи Gmail потребуется для выполнения кода, например, для работы с календарем Google, списками управления доступом, событиями, контактами, настройками и т. д. в этом разделе.
Шаги для создания проекта в Google Developer Console
Ниже приводится пошаговое руководство по созданию проекта в Google Developer Console.
- Перейдите по ссылке https://cloud.google.com/console/project и войдите в систему, используя свои учетные данные Gmail
2. Установите флажок “Я прочитал и согласен со всеми Условиями использования продуктов Google Cloud Platform.” и нажмите кнопку Создать |
3. Запрос на “SMS-подтверждение”. Нажмите кнопку продолжить: |
4. Введите название своей страны и введите номер мобильного телефона. Нажмите кнопку: Отправить код подтверждения |
5. Введите код подтверждения, полученный на ваш мобильный. |
6. В списке API и аутентификация \ API включите статус API Календаря и API Контактов. Выключите все остальные. |
7. На странице API и аутентификация -> Учетные данные нажмите кнопку “СОЗДАТЬ НОВЫЙ ИДЕНТИФИКАТ КЛИЕНТА” в разделе “OAuth”. Выберите “Установленное приложение” и “Другое” из предложенных вариантов и нажмите кнопку “Создать идентификатор клиента”. Запишите здесь идентификатор клиента и секрет клиента, которые будут использоваться в примерах кода в этом разделе. |
Вспомогательные классы
Следующие вспомогательные классы необходимы для выполнения примеров кода в этом разделе. Эти классы GoogleOAuthHelper
и GoogleUser
служат только для упрощения демонстрации. Методы в этих классах используют непубличную структуру веб-страниц, которая может изменяться в любое время.
Класс GoogleOAuthHelper
Следующий фрагмент кода показывает, как реализовать класс GoogleOAuthHelper
.
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.IO;
using System.Net;
using System.Security.Cryptography;
using System.Text;
/// <summary>
/// Developer console:
/// https://console.cloud.google.com/projectselector2
/// Documentation:
/// https://developers.google.com/identity/protocols/oauth2/native-app
/// </summary>
internal class GoogleOAuthHelper
{
public const string AUTHORIZATION_URL = "https://accounts.google.com/o/oauth2/v2/auth";
public const string TOKEN_REQUEST_URL = "https://oauth2.googleapis.com/token";
public const string REDIRECT_URI = "urn:ietf:wg:oauth:2.0:oob";
public const string REDIRECT_TYPE = "code";
public static string codeVerifier;
public static string codeChallenge;
public static CodeChallengeMethod codeChallengeMethod = CodeChallengeMethod.S256;
public const string SCOPE =
"https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fcalendar" + // Calendar
"+" +
"https%3A%2F%2Fwww.google.com%2Fm8%2Ffeeds%2F" + // Contacts
"+" +
"https%3A%2F%2Fmail.google.com%2F"; // IMAP & SMTP
static GoogleOAuthHelper()
{
CreateCodeVerifier();
CreateCodeChallenge();
}
internal static string CreateCodeVerifier()
{
string allowedChars = "0123456789AaBbCcDdEeFfGgHhIiJjKkLlMmNnOoPpQqRrSsTtUuVvWwXxYyZz-._~";
const int minLength = 43;
const int maxLength = 128;
Random random = new Random();
int length = minLength + random.Next(maxLength - minLength);
List<char> codeVerifierChars = new List<char>();
for (int i = 0; i < length; i++)
{
int index = random.Next(allowedChars.Length);
codeVerifierChars.Add(allowedChars[index]);
}
return codeVerifier = string.Join("", codeVerifierChars.ToArray());
}
internal static string CreateCodeChallenge()
{
if (codeChallengeMethod == CodeChallengeMethod.Plain)
return codeChallenge = codeVerifier;
byte[] hashValue = null;
using (SHA256 sha256 = SHA256.Create())
hashValue = sha256.ComputeHash(Encoding.ASCII.GetBytes(codeVerifier));
string b64 = Convert.ToBase64String(hashValue);
b64 = b64.Split('=')[0];
b64 = b64.Replace('+', '-');
b64 = b64.Replace('/', '_');
return codeChallenge = b64;
}
internal static string GetAuthorizationCodeUrl(GoogleUser user)
{
return GetAuthorizationCodeUrl(user, SCOPE, REDIRECT_URI, REDIRECT_TYPE);
}
internal static string GetAuthorizationCodeUrl(
GoogleUser user, string scope, string redirectUri, string responseType)
{
string state = System.Web.HttpUtility.UrlEncode(Guid.NewGuid().ToString());
string approveUrl = AUTHORIZATION_URL +
$"?client_id={user.ClientId}&redirect_uri={redirectUri}&response_type={responseType}&scope={scope}&" +
$"code_challenge={codeChallenge}&code_challenge_method={codeChallengeMethod.ToString()}&" +
$"state={state}";
return approveUrl;
}
internal static TokenResponse GetAccessTokenByRefreshToken(GoogleUser user)
{
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(TOKEN_REQUEST_URL);
request.CookieContainer = new CookieContainer();
request.Method = "POST";
request.ContentType = "application/x-www-form-urlencoded";
string clientId = System.Web.HttpUtility.UrlEncode(user.ClientId);
string clientSecret = System.Web.HttpUtility.UrlEncode(user.ClientSecret);
string refreshToken = System.Web.HttpUtility.UrlEncode(user.RefreshToken);
string grantType = System.Web.HttpUtility.UrlEncode("refresh_token");
string encodedParameters = $"client_id={clientId}&client_secret={clientSecret}&refresh_token={refreshToken}&grant_type={grantType}";
byte[] requestData = Encoding.UTF8.GetBytes(encodedParameters);
request.ContentLength = requestData.Length;
if (requestData.Length > 0)
using (Stream stream = request.GetRequestStream())
stream.Write(requestData, 0, requestData.Length);
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
string responseText = null;
using (TextReader reader = new StreamReader(response.GetResponseStream(), Encoding.ASCII))
responseText = reader.ReadToEnd();
TokenResponse tokensResponse = JsonConvert.DeserializeObject<TokenResponse>(responseText);
return tokensResponse;
}
internal static TokenResponse GetAccessTokenByAuthCode(string authorizationCode, GoogleUser user)
{
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(TOKEN_REQUEST_URL);
request.CookieContainer = new CookieContainer();
request.Method = "POST";
request.ContentType = "application/x-www-form-urlencoded";
string clientId = System.Web.HttpUtility.UrlEncode(user.ClientId);
string clientSecret = System.Web.HttpUtility.UrlEncode(user.ClientSecret);
string authCode = System.Web.HttpUtility.UrlEncode(authorizationCode);
string redirectUri = System.Web.HttpUtility.UrlEncode(REDIRECT_URI);
string grantType = System.Web.HttpUtility.UrlEncode("authorization_code");
string encodedParameters = $"client_id={clientId}&client_secret={clientSecret}&code={authCode}&code_verifier={codeVerifier}&redirect_uri={redirectUri}&grant_type={grantType}";
byte[] requestData = Encoding.UTF8.GetBytes(encodedParameters);
request.ContentLength = requestData.Length;
if (requestData.Length > 0)
using (Stream stream = request.GetRequestStream())
stream.Write(requestData, 0, requestData.Length);
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
string responseText = null;
using (TextReader reader = new StreamReader(response.GetResponseStream(), Encoding.ASCII))
responseText = reader.ReadToEnd();
TokenResponse tokensResponse = JsonConvert.DeserializeObject<TokenResponse>(responseText);
return tokensResponse;
}
public enum CodeChallengeMethod
{
S256,
Plain
}
}
Помощник Google OAuth должен использоваться следующим образом:
- Сначала необходимо сгенерировать URL-адрес кода авторизации.
- Откройте URL-адрес в браузере и завершите все операции. В результате вы получите код авторизации.
- Используйте код авторизации, чтобы получить токен обновления.
- Когда токен обновления существует, вы можете использовать его для получения токенов доступа.
GoogleUser user = new GoogleUser(email, password, clientId, clientSecret);
string authUrl = GoogleOAuthHelper.GetAuthorizationCodeUrl(user);
Console.WriteLine("Перейдите по следующему URL-адресу и получите свой код авторизации:");
Console.WriteLine(authUrl);
Console.WriteLine();
Console.WriteLine("Введите код авторизации:");
string authorizationCode = Console.ReadLine();
Console.WriteLine();
TokenResponse tokenInfo = GoogleOAuthHelper.GetAccessTokenByAuthCode(authorizationCode, user);
Console.WriteLine("Токен обновления получен:");
Console.WriteLine(tokenInfo.RefreshToken);
Console.WriteLine();
user.RefreshToken = tokenInfo.RefreshToken;
tokenInfo = GoogleOAuthHelper.GetAccessTokenByRefreshToken(user);
Console.WriteLine("Получен новый токен доступа:");
Console.WriteLine(tokenInfo.AccessToken);
Console.WriteLine();
Класс GoogleUser
Следующий фрагмент кода показывает, как реализовать класс GoogleUser
.
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
public class GoogleUser
{
public GoogleUser(string email, string password, string clientId, string clientSecret)
: this(email, password, clientId, clientSecret, null)
{
}
public GoogleUser(string email, string password, string clientId, string clientSecret, string refreshToken)
{
Email = email;
Password = password;
ClientId = clientId;
ClientSecret = clientSecret;
RefreshToken = refreshToken;
}
public readonly string Email;
public readonly string Password;
public readonly string ClientId;
public readonly string ClientSecret;
public string RefreshToken;
}
Класс TokenResponse
Следующий фрагмент кода показывает, как реализовать класс TokenResponse
.
// For complete examples and data files, please go to https://github.com/aspose-email/Aspose.Email-for-.NET
using Newtonsoft.Json;
public class TokenResponse
{
[JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "access_token", Required = Required.Default)]
public string AccessToken { get; set; }
[JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "token_type", Required = Required.Default)]
public string TokenType { get; set; }
[JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "expires_in", Required = Required.Default)]
public int ExpiresIn { get; set; }
[JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "refresh_token", Required = Required.Default)]
public string RefreshToken { get; set; }
[JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "scope", Required = Required.Default)]
public string Scope { get; set; }
}